我试图从提示输入选项中分配一个变量而没有运气。如果用户输入1,我想要target_db_name =“database2”。 我的代码:
while true; do
read -p "What is the table name?" table_name
table_name=${table_name,,}
if hdfs dfs -test -e /foo/$table_name ;
then read -p "What is the target database you want to copy the
“foo.${table_name}” table to?
Your three options are:
1) database1
2) database2
3) database3
Type 1, 2, or 3: " target_db;
(((Here is where I want to state if $target_db = "1" then target_db_name
= "database1", if $target_db = "2" then target_db_name = "database2" etc...)))
read -p "Would you like to begin the HDFS copy with the following configuration:
Target Database: ${target_db_name}
Table Name: ${table_name}
Continue (Y/N):"
else echo "Please provide a valid table name.
Exiting this script" ; exit ; fi
done
我尝试过创建另一个没有运气的if语句。
"....Type 1, 2, or 3: " target_db;
else if $target_db = "1" then target_db_name = "edw_qa_history"; fi
答案 0 :(得分:1)
if $target_db = "1" then
将不起作用,因为if
后面的内容必须是命令,而不是测试表达式。现在,if
语句中使用的最常见命令是[
(是的,这实际上是一个命令名称;它与test
命令同义),它接受一个测试表达式(并且关闭)括号)作为参数,成功或失败取决于表达式是否为真。所以正确的语法是这样的:
if [ "$target_db" = "1" ]; then
请注意,还有两个与你所拥有的不同之处:我在变量引用周围加上双引号(几乎总是一个好主意,以避免可能解析奇数),并在then
之前添加一个分号(需要指示[
结束的参数和shell语法的恢复位置。我还注意到你脚本的许多行末尾都有分号;这不是必需的,行尾足以表示命令的结束。只有当你在同一行上有另一个命令(或类似then
之类的命令)时才需要分号作为分隔符。
但是,正如@Barmar在评论中指出的那样,case
可能比这里的if
和elif
语句列表更好。 case
专门用于将字符串与其他字符串(或模式)的列表进行比较,并根据匹配的字符串执行不同的操作。它看起来像这样:
case "$target_db" in
1) target_db_name="database1" ;;
2) target_db_name="database2" ;;
3) target_db_name="database3" ;;
*) "Please provide a valid table name. Exiting this script" ; exit ;;
esac
这里,即使在一行的末尾,也需要双分号 来表示每种情况的结束。另请注意,*
模式(最后一种情况)与任何内容匹配,因此它在else
... if
...序列中的作用类似于elif
。
最后注意事项:使用shellcheck.net来验证您的代码。
答案 1 :(得分:0)
您不需要if
语句将数字映射到数组;你只需要一个阵列。
db_names=(
"datebase 1"
"database 2"
"database 3"
)
# ...
target_db_name=${db_names[$target_db - 1]}
if [[ -z $target_db_name ]]; then
exit
fi