makefile变量赋值

在定义变量的值时,我们可以使用其它变量来构造变量的值,在Makefile中有两种方式来在用变量定义变量的值。先看第一种方式,也就是简单的使用“=”号,在“=”左侧是变量,右侧是变量的值,右侧变量的值可

大家好,又见面了,我是全栈君,今天给大家准备了Idea注册码。

在定义变量的值时,我们可以使用其它变量来构造变量的值,在Makefile中有两种方式来在用变量定义变量的值。

先看第一种方式,也就是简单的使用“=”号,在“=”左侧是变量,右侧是变量的值,右侧变量的值可以定义在文件的任何一处,也就是说,右侧中的变量不一定非要是已定义好的值,其也可以使用后面定义的值。如:

foo = $(bar)
bar = $(ugh)
ugh = Huh?

all:
echo $(foo)

我们执行“make all”将会打出变量$(foo)的值是“Huh?”( $(foo)的值是$(bar),$(bar)的值是$(ugh),$(ugh)的值是“Huh?”)可见,变量是可以使用后面的变量来定义的。

这个功能有好的地方,也有不好的地方,好的地方是,我们可以把变量的真实值推到后面来定义,如:

CFLAGS = $(include_dirs) -O
include_dirs = -Ifoo -Ibar

当“CFLAGS”在命令中被展开时,会是“-Ifoo -Ibar -O”。但这种形式也有不好的地方,那就是递归定义,如:

CFLAGS = $(CFLAGS) -O

或:

A = $(B)
B = $(A)

这会让make陷入无限的变量展开过程中去,当然,我们的make是有能力检测这样的定义,并会报错。还有就是如果在变量中使用函数,那么,这种方式会让我们的make运行时非常慢,更糟糕的是,他会使用得两个make的函数“wildcard”和“shell”发生不可预知的错误。因为你不会知道这两个函数会被调用多少次。http://hovertree.com/menu/linux/

为了避免上面的这种方法,我们可以使用make中的另一种用变量来定义变量的方法。这种方法使用的是“:=”操作符,如:

x := foo
y := $(x) bar
x := later

其等价于:

y := foo bar
x := later

值得一提的是,这种方法,前面的变量不能使用后面的变量,只能使用前面已定义好了的变量。如果是这样:

y := $(x) bar
x := foo

那么,y的值是“bar”,而不是“foo bar”。

上面都是一些比较简单的变量使用了,让我们来看一个复杂的例子,其中包括了make的函数、条件表达式和一个系统变量“MAKELEVEL”的使用:

ifeq (0,${MAKELEVEL})
cur-dir := $(shell pwd)
whoami := $(shell whoami)
host-type := $(shell arch)
MAKE := ${MAKE} host-type=${host-type} whoami=${whoami}
endif

关于条件表达式和函数,我们在后面再说,对于系统变量“MAKELEVEL”,其意思是,如果我们的make有一个嵌套执行的动作(参见前面的“嵌套使用make”),那么,这个变量会记录了我们的当前Makefile的调用层数。

下面再介绍两个定义变量时我们需要知道的,请先看一个例子,如果我们要定义一个变量,其值是一个空格,那么我们可以这样来:

nullstring :=
space := $(nullstring) # end of the line

nullstring 是一个Empty变量,其中什么也没有,而我们的space的值是一个空格。因为在操作符的右边是很难描述一个空格的,这里采用的技术很管用,先用一个 Empty变量来标明变量的值开始了,而后面采用“#”注释符来表示变量定义的终止,这样,我们可以定义出其值是一个空格的变量。请注意这里关于“#”的使用,注释符“#”的这种特性值得我们注意,如果我们这样定义一个变量:

dir := /foo/bar # directory to put the frobs in

dir这个变量的值是“/foo/bar”,后面还跟了4个空格,如果我们这样使用这样变量来指定别的目录——“$(dir)/file”那么就完蛋了。

还有一个比较有用的操作符是“?=”,先看示例:

FOO ?= bar

其含义是,如果FOO没有被定义过,那么变量FOO的值就是“bar”,如果FOO先前被定义过,那么这条语将什么也不做,其等价于:

ifeq ($(origin FOO), undefined)
FOO = bar
endif

 

推荐:http://www.cnblogs.com/roucheng/p/3470287.html

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/120427.html原文链接:https://javaforall.net

(0)
上一篇 2021年12月25日 下午5:00
下一篇 2021年12月25日 下午6:00


相关推荐

  • MySQL · 性能优化· CloudDBA SQL优化建议之统计信息获取

    MySQL · 性能优化· CloudDBA SQL优化建议之统计信息获取

    2022年3月7日
    39
  • vue解决跨域_java跨域解决方案

    vue解决跨域_java跨域解决方案现阶段跨域方式有很多种,但是基本思想只有两种:绕过同源策略:历史遗留的产物,虽然思想很好,但是局限性太大(仅支持、因为数据是在中,所以携带数据小)。:通过反向代理绕过去,这是很完美的解决方案,加上会给服务器增加一点压力,不过这点压力问题并不大[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ddoEgRFd-1656482203293)(https://juejin.cn/)][外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-4M4avsX0-1

    2026年4月19日
    5
  • 解析excel拼接SQL 小脚本

    解析excel拼接SQL 小脚本

    2020年11月19日
    195
  • Ubuntu安装Redis6.2.6

    Ubuntu安装Redis6.2.6文章目录 Redis 安装 1 下载地址 2 安装版本 3 安装步骤 3 1 准备工作 安装最新版本的 gcc 编译器 3 2 将下载好的 redis 6 2 6 tar gz 放在 usr local 目录下 4 默认安装目录 5 后台启动 5 1 备份 redis conf5 2 后台启动设置 daemonizeno 改成 yes5 3Redis 启动 5 4Redis 关闭 Redis 安装 1 下载地址官网地址 https redis io 2 安装版本 redis 6 2 6 tar gz 安装在 Linux 上 3 安装步骤 3

    2026年1月29日
    1
  • java设计模式3,里氏替换原则

    java设计模式3,里氏替换原则里氏替换原则的内容可以描述为:“派生类(子类)对象可以在程序中代替其基类(超类)对象。”

    2025年7月3日
    6
  • vue 生成二维码 插件

    vue 生成二维码 插件1.下载qr插件npmivue-qr–save2.引入//引入插件importVueQrfrom’vue-qr’//放入componentscomponents:{VueQr}3.使用//页面使用<vue-qrtext=”这是你的二维码内容”size=”200″:margin=”0″/>4.效果

    2022年10月3日
    3

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号