Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/bash/17.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/shell/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
用于从文本生成csv文件的Bash脚本_Bash_Shell_Sh_Export To Csv - Fatal编程技术网

用于从文本生成csv文件的Bash脚本

用于从文本生成csv文件的Bash脚本,bash,shell,sh,export-to-csv,Bash,Shell,Sh,Export To Csv,我有一个包含记录的文本文件: Data1 Data2 ... Data50 我必须以以下格式从上述文本文件创建.csv文件: Type | Count | Name Def | u1 | Data1 Def | u2 | Data2 .... | ..... | .... Def | u50 | Data50 我需要一个bash脚本来从文本文件生成.csv文件。我不熟悉shell脚本!我也学习了awk和sed的基

我有一个包含记录的文本文件:

  Data1

  Data2

  ...

  Data50
我必须以以下格式从上述文本文件创建.csv文件:

Type |  Count | Name

Def |    u1 |    Data1

Def |    u2  |     Data2

....  |  .....   |  ....

Def  |   u50   | Data50
我需要一个bash脚本来从文本文件生成.csv文件。我不熟悉shell脚本!我也学习了awk和sed的基础知识。 我有一个模糊的想法,比如:

#!/bin/bash
type="Def"
x=1
count="u"
for F in ../test.txt
do
    {
       read \n
       echo "$type, $count$x, $..." >> ../test.csv
       x=x+1
    } < $F

done 
#/bin/bash
type=“Def”
x=1
count=“u”
对于../test.txt中的F
做
{
读取\n
echo“$type,$count$x,$…”>>../test.csv
x=x+1
}<$F
完成
我知道字段分隔符是“\n”。从那以后我有点迷路了


谢谢

第二个字段是:

x = `expr $x + 1`
$count$x
整个脚本变为:

#!/bin/sh

echo Type,Count,Name > test.csv
x=0
for f in `cat test.txt`
do
   x=`expr $x + 1`
   echo Def,u$x,$f >> test.csv
done

祝你好运

Your
for
循环将只循环一次,它循环您列出的令牌,而您只列出了一个(看起来像文件名,所以我猜您希望循环文件中的行):

在循环外部重定向更有效,因为shell不必关闭并重新打开输出文件

如果要在命令行上传入变量文件名,只需将硬编码的
。/test.txt
替换为
“$1”
。您可以类似地参数化输出文件名,但我只需删除输出重定向,并让调用方决定如何处理脚本的输出

如果需要读取多个字段并用逗号拆分,请调整
IFS

nl -s , ../test.txt |
while IFS=, read -r i first second rest; do
    printf "%i,%s,u%i,%s\n" $i "$first" "$second" "$rest"
done

printf
建议优先于
echo
,尤其是在您的输出要求不重要的情况下。我没有特别引用
$I
,以消除
nl
在行号之前添加的任何前导空格。否则,除非您特别指定,否则通常应在变量周围使用双引号要求shell对值执行空白标记化和通配符扩展。)

如果已安装perl,则

perl -lnE 'say qq{Def,u$.,"$_"}' < inputfile
那么

seq -f 'Some Data%g' 50 | perl -lnE 'say qq{Def,u$.,"$_"}'
印刷品

Def,u1,"Some Data1"
Def,u2,"Some Data2"
...
Def,u49,"Some Data49"
Def,u50,"Some Data50"
我引用了最后一个字段,因为在输入中可以得到
或空格

基于@Roland comment,添加标题行:

cat data | (echo 'Type,Count,Name' ; perl -lnE 'say qq{Def,u$.,"$_"}')

如果您想要
bash
解决方案,只需使用:

cat -n filename | sed 's/ *\(.*\)\t\(.*\)/Def,u\1,"\2"/'
还是拯救世界

cat -n - | sed 's/ *\(.*\)\t\(.*\)/Def,u\1,"\2"/'
输入一些文件,如“makecsv”,并将其用作

./makecsv < data
/makecsv<数据

Ps:hmm.@tripleee的
nl
短为
cat-n
;)

将其保存在一个文件中,例如makecsv.rc:

#!/bin/sh
echo Type,Count,Name
x=0
for f in `cat`
do
   x=`expr $x + 1`
   echo Def,u$x,$f
done
然后运行为:

cat  ../test.txt | ./makecsv.rc > ../test.csv
如果需要,您可以执行
chmod+x makecsv.rc


优点是输入/输出文件名不是硬编码的!谢谢我错过了。谢谢你!但是我被困在如何将“Data1,Data2…Data50”从.txt文件写入一个新的.csv文件中。我用Cygnus在我的台式电脑上测试了这一点,同时在笔记本电脑上执行stackoverflow,所以我不得不重新键入它。我打字出错了吗?你是对的。我使用带反引号的
cat
进行了更正。抱歉回答得太快:-)我尝试了你的代码,但for循环似乎不适用于catcommand@Pbms
read
可以读取多个变量,只需列出所需的字段即可<代码>读取时-r第一秒休息;做不要忘记csv标题行!这仍然很容易添加到您的解决方案中
x=((x+1))
对我不起作用,太糟糕了,我不喜欢
expr
@Roland使用
x=$((x+1))
让x++
非常感谢您花时间。你说得对,我想读一个文件中的多行。就像我提到的,我对bash脚本还不熟悉。所以我尝试了你提供的第一个代码,它给了我“done”的语法错误!你能给我一些关于外部实用程序的细节吗?有很好的理由省略标题行。因为OP的例子也没有,所以我没有添加一个;如果有标题行,建议不要使用。在此处添加csv标题行也很容易。对此很抱歉,但目前我正在处理大量csv文件,令人惊讶的是,标题行经常被无故省略。即使是包含24列的csv文件……如果不想硬编码文件名,也只需使用
“$1”
“$2”
。backticks中的
cat
非常可怕。这非常有帮助,因为我需要使用不同的文件以一定的间隔执行它!非常感谢@你说得对。但在我的时区,肯定是该回家的时候了。请建议如何避免脚本和命令行中的两个
cat
s:问题。我在自己的答案中添加了一个片段。你的可以进行类似的重构,但答案几乎相同…@Roland我的评论是针对其他用户的,他们可以使用该解决方案,他们可以拥有一个空间。记住,答案也是为未来的用户准备的。我不想批评你的答案,但老实说,我同意@tripleee——backtick中简单的
cat
非常可怕,它反对任何良好的bash实践。此外,在任何现代shell中,
$(命令)
作为backticks更为可取。
cat -n - | sed 's/ *\(.*\)\t\(.*\)/Def,u\1,"\2"/'
./makecsv < data
#!/bin/sh
echo Type,Count,Name
x=0
for f in `cat`
do
   x=`expr $x + 1`
   echo Def,u$x,$f
done
cat  ../test.txt | ./makecsv.rc > ../test.csv