3

SCons の Glob 結果から特定のソース ファイルを除外したい場合があります。通常、そのソース ファイルをさまざまなオプションでコンパイルしたいからです。このようなもの:

objs = env.Object(Glob('*.cc'))
objs += env.Object('SpeciallyTreatedFile.cc', CXXFLAGS='-O0')

もちろん、それは SCons に問題を引き起こします:

scons: *** Two environments with different actions were specified
       for the same target: SpeciallyTreatedFile.o

私は通常、次のイディオムを使用してこれを回避します。

objs = env.Object([f for f in Glob('*.cc')
  if 'SpeciallyTreatedFile.cc' not in f.path])

しかし、これは非常に醜く、フィルターで除外するファイルが複数ある場合はさらに醜くなります。

これを行うためのより明確な方法はありますか?

4

2 に答える 2

7

I got fed up duplicating the [f for f in Glob ...] expression in several places, so I wrote the following helper method and added it to the build Environment:

import os.path

def filtered_glob(env, pattern, omit=[],
  ondisk=True, source=False, strings=False):
    return filter(
      lambda f: os.path.basename(f.path) not in omit,
      env.Glob(pattern))

env.AddMethod(filtered_glob, "FilteredGlob");

Now I can just write

objs = env.Object(env.FilteredGlob('*.cc',
  ['SpeciallyTreatedFile.cc', 'SomeFileToIgnore.cc']))
objs += env.Object('SpeciallyTreatedFile.cc', CXXFLAGS='-O0')

Using this pattern it would be easy to write something similar that uses, say, a regexp filter as the omit argument instead of a simple list of filenames, but this works well for my current needs.

于 2012-09-20T18:30:57.583 に答える