一个脚本中的多个目标,复制到Makefile中的多个不同目录

问题描述 投票:0回答:1

场景

我正在努力更新一个脚本,该脚本在构建时为我们的每个构建生成CJava的源代码文件。
这需要在 Windows 和 Linux 上运行。
需要为每种语言创建两种文件类型:EnumsTables

每组四个文件(C Enum、C Table、Java Enum、Java Table)都是从相应的 CSV 文件生成的。
给定一个名为

A.csv
的输入 CSV 文件,输出文件为
AEnum.inc
ATable.inc
AEnum.java
ATable.java

可以通过调用 python 脚本并激活 venv 来一次创建所有四个文件,如下所示:

python main.py --input A.csv --output ./output --enum-c --table-c --enum-java --table-java

在 makefile 中使用名为

run_autogen_all
的函数对其进行了缩短。

创建文件后,需要将它们复制到不同的目录:

  • C 枚举和表格进入
    $(C_AUTOGEN)/
  • Java 枚举进入
    $(JAVA_ENUM)/
  • Java 表进入
    $(JAVA_TABLE)/

问题

我无法弄清楚如何确保 python 脚本只运行一次(运行时是不可忽略的),同时还将所有文件复制到正确的目录。

如何使用 Make 实现此行为?

尝试过的解决方案

这是我当前的解决方案,有效,但它运行 python 脚本两次并复制文件两次。

MAIN_4_CSV_FILES = A.CSV B.CSV C.CSV D.CSV E.CSV F.CSV G.CSV H.CSV I.CSV J.CSV K.CSV L.CSV M.CSV N.CSV O.CSV P.CSV Q.CSV R.CSV S.CSV T.CSV U.CSV V.CSV W.CSV X.CSV Y.CSV Z.CSV
.PHONY : JavaFiles CFiles
JavaFiles : *.java
CFiles : *.inc

*.java *.inc : $(MAIN_4_CSV_FILES)
    $(call run_autogen_all,$^)
    $(COPYF) *Enum.java $(JAVA_ENUM)
    $(COPYF) *Table.java $(JAVA_TABLE)
    $(COPYF) *.inc $(C_AUTOGEN)

运行

make JavaFiles CFiles -n
给出以下输出

python "../../../../../build/Common/CSV_Parser/autogenerate_from_csv.py" --output "./" --csv-files A.CSV B.CSV C.CSV D.CSV E.CSV F.CSV G.CSV H.CSV I.CSV J.CSV K.CSV L.CSV M.CSV N.CSV O.CSV P.CSV Q.CSV R.CSV S.CSV T.CSV U.CSV V.CSV W.CSV X.CSV Y.CSV Z.CSV
cp -f *Enum.java ../../../../Project/java/enums
cp -f *Table.java ../../../../Project/java/tables
cp -f *Enum.inc ../../../../Project/c
cp -f *Table.inc ../../../../Project/c
python "../../../../../build/Common/CSV_Parser/autogenerate_from_csv.py" --output "./" --csv-files A.CSV B.CSV C.CSV D.CSV E.CSV F.CSV G.CSV H.CSV I.CSV J.CSV K.CSV L.CSV M.CSV N.CSV O.CSV P.CSV Q.CSV R.CSV S.CSV T.CSV U.CSV V.CSV W.CSV X.CSV Y.CSV Z.CSV
cp -f *Enum.java ../../../../Project/java/enums
cp -f *Table.java ../../../../Project/java/tables
cp -f *Enum.inc ../../../../Project/c
cp -f *Table.inc ../../../../Project/c

之前的尝试

我尝试了很多选择,以下是一些不起作用的

%Enum.inc %Enum.java %Table.inc %Table.java :
    $(call run_autogen_all,$<)
    $(call copy_attrib,$(notdir $@),$@)

AFiles = $(C_AUTOGEN)/AEnum.c $(C_AUTOGEN)/ATable.c $(JAVA_ENUM)/AEnum.java $(JAVA_TABLE)/ATable.java
$(AFiles) : A.csv
[...]
JavaEnums : $(JAVA_ENUM)/AEnum.java $(JAVA_ENUM)/BEnum.java [...]

$(JAVA_ENUM)/%Enum.java : %Enum.java
    $(call run_autogen_all,$*.csv)
    $(call copy_attrib,$(notdir $@),$@)
[...]
%Enum.java %Enum.c %Table.java %Table.c : %.csv
    $(call run_autogen_all,$<)
    $(call copy_attrib,$(notdir $@),$@)
[...]

我也尝试过弄乱

.INTERMEDIATE
.SECONDARY
,但无济于事。

python csv makefile
1个回答
0
投票

假设您使用 GNU make 并且所有生成的文件都在当前目录中生成,您可以使用具有 4 个目标的模式规则。

.PHONY: all
all: $(C_AUTOGEN)/AEnum.inc $(C_AUTOGEN)/ATable.inc $(JAVA_ENUM)/AEnum.java $(JAVA_TABLE)/ATable.java

$(C_AUTOGEN)/%Enum.inc $(C_AUTOGEN)/%Table.inc $(JAVA_ENUM)/%Enum.java $(JAVA_TABLE)/%Table.java: %.csv
   python main.py --input $< --output ./output --enum-c --table-c --enum-java --table-java
   mv $*Enum.inc $*Table.inc $(C_AUTOGEN)
   mv $*Enum.java $(JAVA_ENUM)
   mv $*Table.java $(JAVA_TABLE)

使用最新版本的 GNU make,您还可以使用分组目标 (

&:
):

$(C_AUTOGEN)/AEnum.inc $(C_AUTOGEN)/ATable.inc $(JAVA_ENUM)/AEnum.java $(JAVA_TABLE)/ATable.java &: A.csv
    python main.py --input $< --output ./output --enum-c --table-c --enum-java --table-java
   mv AEnum.inc ATable.inc $(C_AUTOGEN)
   mv AEnum.java $(JAVA_ENUM)
   mv ATable.java $(JAVA_TABLE)

在这两种情况下,GNU make 仅执行一次配方来构建 4 个目标。不要在此类规则的配方中使用

$@
(至少在阅读文档之前不要使用)。

一旦你测试了这个,也许可以尝试重新引入你的宏。

© www.soinside.com 2019 - 2024. All rights reserved.