我正在研究一个非常简单的bash脚本,我遇到了一个问题,即低估了为什么弃用$ []工作正常,而$(())似乎打破了整个事情。
我所指的代码是:
for i in {1..10};
do
printf %4d $[{1..10}*i]
echo
done
在这个版本中我没有任何问题,但我不想使用已弃用的bash元素,这就是我想切换到$(())的原因。
不幸的是,只要我将代码更改为:
printf %4d $(({1..10}*i))
我收到错误:
./script_bash.sh: line 8: {1..10}*i: syntax error: argument expected (error token is "{1..10}*i")
我会感谢你对这个的帮助......
答案 0 :(得分:3)
为1990年设置背机。
Bash实现了每个POSIX P1003.2d9(大约1990年)的$[]
语法,这是已发布的P1003.2-1992的草案。在草案和标准之间的两年中,POSIX已经确定了ksh88 $(())
语法和行为。 Chet Ramey(bash maintainer)有这样说,back in 2012:
Bash ......实施了$ [...],因为没有其他的 当时的语法,并获得一些操作经验 shell中的算术扩展。 Bash-1.14 ...列出了两种形式的算术扩展,但是 时间bash-2.0于1995年发布,手册仅提到 $((...))表格。
这向我建议$[]
形式是 experimental ,并且当POSIX采用$(())
语法时,它具有指定为遗忘的某些行为(如大括号扩展) 。那些实验行为留在了,因为已经存在依赖它们的野外脚本(记得已经过去了2年多)。
切特在同一个帖子中明确表示$[]
表单已过时,但未弃用:
现在,继续拖动$ [...]语法几乎没有任何问题。 它只需要几十个字节的代码。我没有计划将其删除。
current POSIX standard, C.2.6 Word Expansions > Arithmetic Expansion提到语法(强调我的):
在早期提案中,使用了表单$ [表达式]。 它在功能上等同于" $(())"目前的文字,但提出反对意见,即1988年KornShell已经实施了#34; $(())"并没有令人信服的理由发明另一种语法。此外," $ []"语法与case语句中的模式有轻微的不兼容性。
所以bash中实现的行为并不符合规范,但由于没有计划将其删除,我认为没有理由放弃它的好处,如果它能整齐地解决你的问题。但是,正如@Barmar的评论所指出的那样,对这些代码进行评论并将其链接在这里是一个好主意,以便未来的开发人员知道你的意思是什么!
答案 1 :(得分:1)
$(())
用于算术表达式,并且括号扩展不在算术中完成。
使用循环创建一个数组:
for i in {1..10}
do
vals=()
for j in {1..10}
do
vals+=($((i*j)))
done
printf "%4d" ${vals[@]}
done
答案 2 :(得分:1)
bash
{}
中扩展参数的顺序,不起作用。大括号扩展($(())
)比bash
的算术扩展(man bash
)更早完成。如果是相反的话,你的代码肯定会有效。
来自def isRoot(n, root):
return not math.log(n, root)%1
:
扩展的顺序是:支撑扩展;代码扩展,参数和变量扩展,算术扩展和命令替换(以从左到右的方式完成);分词;和路径名扩展。
答案 3 :(得分:0)
遇到这样的重击。这个问题需要解释,而不是解决方案,但这是一种表达这种方式的$(())方式。
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
from keras.models import Model
from keras.layers import Input, Dense, Dropout, Flatten
from keras.layers import Conv2D, MaxPooling2D
def build_model(input_shape, num_classes):
"""
Builds the model architecture based on MNIST CNN
https://www.tensorflow.org/tutorials/estimators/cnn
Args:
input_spape: Input shape of the model
num_classes: Number of classes
Returns:
keras.models.Model: The created model
"""
inputs = Input(shape=input_shape)
x = Conv2D(32, (5,5), activation='relu')(inputs)
x = MaxPooling2D(pool_size=(2, 2))(x)
x = Conv2D(128, (3, 3), activation='relu')(x)
x = MaxPooling2D(pool_size=(2, 2))(x)
x = Dropout(0.2)(x)
x = Flatten()(x)
x = Dense(512, activation='relu')(x)
x = Dense(256, activation='relu')(x)
predictions = Dense(num_classes, activation='softmax')(x)
return Model(inputs=inputs, outputs=predictions)
像参数扩展一样,在算术扩展中禁止括号扩展。
(打击手册)
为避免与参数扩展冲突,请不要使用字符串“ $ {” 被认为适合大括号扩张,并禁止大括号扩张 直到结尾的“}”。