简体   繁体   中英

Makefile: no target error even when target and dependency exist

My makefile:

./corpus/%.spacy : ./assets/%.json
     python3 ./scripts/convert.py $< $@

Two questions:

  1. Even if A.spacy and A.json exist and A.json is updated more recently than A.spacy, I get the following output.

     $ make $ make: *** No targets. Stop.
  2. What to add to have it make A.spacy if only A.json exists? I tried the below code, which didn't work and I feel I'm not fully understanding targets and dependencies in makefiles.

     convert: ./corpus/%.spacy python3./scripts/convert.py $(./scripts/$*.json) $<./corpus/%.spacy: ./assets/%.json echo $?

Didn't work as in gave the following output

$ make convert
$ make: *** No rule to make target `corpus/%.spacy', needed by `convert'.  Stop.

You seem to be thinking that declaring a pattern rule will cause make to go spelunking your directory looking for all possible ways to use that pattern, as if it were a wildcard or something akin to ls *.spacy .

That's not what a pattern rule is.

A pattern rule is a template that make can apply if it wants to build a given target and it doesn't know how to build that target.

If you have the above makefile it just tells make "hey, if you happened to want to create a target that matches the pattern ./corpus/%.spacy then here's a way to do it". If you type make with no arguments, then you haven't told make that you want to build anything so it won't use your pattern rule.

If you type:

$ make ./corpus/A.spacy

now you've told make you want to actually build something ( ./corpus/A.spacy ), so now make will try to build that thing, and it will see your pattern rule and it will try to use it.

As for the other, this:

convert : ./corpus/%.spacy
        python3 ./scripts/convert.py $(./scripts/$*.json) $<

is not a pattern rule. A pattern rule must have a pattern character ( % ) in the target ; this is defining a target convert that depends on a file named, explicitly, ./corpus/%.spacy of which you don't have any file with that name, so you get that error.

You didn't actually describe what you wanted to do, but I think maybe you want to do something like this:

# Find all the .json files
JSONS := $(wildcard ./corpus/*.json)

# Now figure out all the output files we want
SPACYS := $(patsubst ./corpus/%.json,./corpus/%.spacy,$(JSONS))

# Now create a target that depends on the stuff we want to create
all: $(SPACYS)

# And here's a pattern that tells make how to create ONE spacy file:
./corpus/%.spacy : ./assets/%.json
        python3 ./scripts/convert.py $< $@

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM