Jak wykluczyć pojedynczy plik z wzorca pliku cmake (GLOB…)?

86

Mój CMakeLists.txtzawiera tę linię:

file(GLOB lib_srcs Half/half.cpp Iex/*.cpp IlmThread/*.cpp Imath/*.cpp IlmImf/*.cpp)

a IlmImffolder zawiera b44ExpLogTable.cpp, które muszę wykluczyć z kompilacji.

Jak to osiągnąć?

berak
źródło

Odpowiedzi:

100

Możesz użyć tej listfunkcji do manipulowania listą, na przykład:

list(REMOVE_ITEM <list> <value> [<value> ...])

W twoim przypadku może coś takiego zadziała:

list(REMOVE_ITEM lib_srcs "IlmImf/b44ExpLogTable.cpp")
Lindydancer
źródło
1
oprócz lib_srcs zamiast lib_src i IlmImf zamiast IlmThread, To załatwiło sprawę! wielkie dzięki!
berak
20
Uwaga: Podczas usuwania pozycji z listy upewnij się, że szukana wartość pasuje dokładnie tak, jak na liście. Miałem problemy z miksowaniem $ {CMAKE_SOURCE_DIR} /src/file_to_remove.cpp z $ {CMAKE_CURRENT_SOURCE_DIR} /../ file_to_remove.cpp. Wskazuje to samo miejsce, ale nie jest to ten sam ciąg. wiadomość („$ {VARIABLE_NAME}”) może pomóc w debugowaniu tej zawartości.
hbobenicio
To nie pomaga, jeśli używasz CONFIGURE_DEPENDSi musisz wykluczyć plik utworzony przez kompilację. Filtr na liście po filewywołaniu nadal wywołuje odbudowę, której w moim przypadku staram się uniknąć.
simon.watts
Jest o wiele lepszy w użyciulist(FILTER
hukeping
2
Powyższe rozwiązanie nie działa u mnie z camke w wersji 3.10.2 Ale poniższe rozwiązanie: list(FILTER <list> <INCLUDE|EXCLUDE> REGEX <regular_expression>) u mnie działa dobrze.
MH Yip
42

FILTR to kolejna opcja, która może być wygodniejsza w niektórych przypadkach:

list(FILTER <list> <INCLUDE|EXCLUDE> REGEX <regular_expression>)

Ta linia wyklucza każdy element kończący się wymaganą nazwą pliku:

list(FILTER lib_srcs EXCLUDE REGEX ".*b44ExpLogTable.cpp$")

Oto specyfikacja Regex dla cmake:

The following characters have special meaning in regular expressions:

^         Matches at beginning of input
$         Matches at end of input
.         Matches any single character
[ ]       Matches any character(s) inside the brackets
[^ ]      Matches any character(s) not inside the brackets
 -        Inside brackets, specifies an inclusive range between
          characters on either side e.g. [a-f] is [abcdef]
          To match a literal - using brackets, make it the first
          or the last character e.g. [+*/-] matches basic
          mathematical operators.
*         Matches preceding pattern zero or more times
+         Matches preceding pattern one or more times
?         Matches preceding pattern zero or once only
|         Matches a pattern on either side of the |
()        Saves a matched subexpression, which can be referenced
          in the REGEX REPLACE operation. Additionally it is saved
          by all regular expression-related commands, including
          e.g. if( MATCHES ), in the variables CMAKE_MATCH_(0..9).
Eugene
źródło
Może być znacznie bardziej niezawodny niż grzebanie w bezwzględnych / względnych ścieżkach
EFraim
1
Znacznie lepiej niżlist(REMOVE_ITEM
ceztko
1
Uwaga, która list(FILTER ...)została wprowadzona w cmake v3.6: stackoverflow.com/a/42167646/3476780
yano
To zdecydowanie lepsza odpowiedź, chociaż jeśli próbujesz użyć tego do wykluczenia całego katalogu lub jeśli twoje wyrażenie regularne jest pomieszane, możesz wykluczyć więcej niż chcesz. Na przykład próba wykluczenia .*test/.*może wykluczyć wszystko, jeśli projekt znajduje się w drzewie katalogów, w którym jeden z katalogów nadrzędnych nosi nazwę podobną do mytest.
Anthony D973,
1

Spróbuj tego : CMakeLists.txt

install(DIRECTORY   ${CMAKE_SOURCE_DIR}/ 
            DESTINATION ${CMAKE_INSTALL_PREFIX}
            COMPONENT   copy-files
            PATTERN     ".git*"   EXCLUDE
            PATTERN     "*.in"    EXCLUDE
            PATTERN     "*/build" EXCLUDE)

add_custom_target(copy-files
            COMMAND ${CMAKE_COMMAND} -D COMPONENT=copy-files
            -P cmake_install.cmake)
$cmake <src_path> -DCMAKE_INSTALL_PREFIX=<install_path>
$cmake --build . --target copy-files
James
źródło