Linux 如何修改文本的每一行?

Linux 如何修改文本的每一行?,linux,bash,Linux,Bash,我有一个文件,看起来像这样(它可以有两行以上): 我想这样改变它: user: user1 address: 1.1.1.1 db: DB1 right: SELECT user: userX address: 2.2.2.2 db: DB4 right: SELECT 我认为最简单的方法是使用read功能: !/bin/bash filename='/tmp/temp.txt' while read ; do user=$(cut -d";" -f2 /tmp/temp.txt)

我有一个文件,看起来像这样(它可以有两行以上):

我想这样改变它:

user: user1 address: 1.1.1.1 db: DB1 right: SELECT
user: userX address: 2.2.2.2 db: DB4 right: SELECT
我认为最简单的方法是使用
read
功能:

!/bin/bash

filename='/tmp/temp.txt'
while read ; do
  user=$(cut -d";" -f2 /tmp/temp.txt)
  address=$(cut -d";" -f3 /tmp/temp.txt)
  database=$(cut -d";" -f4 /tmp/temp.txt)
  right=$(cut -d";" -f5 /tmp/temp.txt)

 echo "user:$user address:$address database:$database right:$right"

done < $filename


我希望输出中的行数与输入文件中的行数相同。

只需使用
awk

$ awk -F ';' '{ print "user:", $2, "address:", $3, "db:", $4, "right:", $5 }' your_file

这会将文件的每一行拆分为分号,然后以所需的输出格式打印出所需的列。

请尝试以下操作

awk '
BEGIN{
  FS=";"
  OFS=": "
}
val{
  sub(/: $/,"",val)
  print val
  val=""
}
{
  $1="user"
  $2=$2 " address"
  $3=$3 " db"
  $4=$4" right"
  val=$0
}
END{
  if(val){
    sub(/: $/,"",val)
    print val
  }
}
'   Input_file

如果您想继续使用bash,您走的是正确的道路,但您做的工作太多了:

filename='/tmp/temp.txt'
while read ; do
  user=$(cut -d";" -f2 /tmp/temp.txt)
  address=$(cut -d";" -f3 /tmp/temp.txt)
  database=$(cut -d";" -f4 /tmp/temp.txt)
  right=$(cut -d";" -f5 /tmp/temp.txt)

 echo "user:$user address:$address database:$database right:$right"

done < $filename
但它仍然使用外部命令来实现shell本机可以实现的功能

  • 使用
    IFS
    变量帮助您解析每一行:您有分号分隔的数据,因此可以执行以下操作:

    while IFS=";" read -r empty user address database right empty; do
        echo "user:$user address:$address database:$database right:$right"
    done < $filename
    
    while IFS=“;”读取-r空用户地址数据库右空;做
    echo“user:$user address:$address数据库:$database right:$right”
    完成<$filename
    
    注意“空”变量占位符,用于在第一个分号之前和最后一个分号之后保存数据


  • 使用sed,从左到右逐个替换分号:

    $ sed 's/;/user: /;s/;/ address: /;s/;/ db: /;s/;/ right: /;s/;//' infile
    user: user1 address: 1.1.1.1 db: DB1 right: SELECT
    user: userX address: 2.2.2.2 db: DB4 right: SELECT
    

    我建议看一看
    sed
    ;看到我的答案了。@Shawn,是的,但我确实考虑过,如果有比OP不想更改的字段更多的字段,那么最好不要对所有字段进行硬编码。写
    print“user:”,$2,“address”…
    ,可能会更简洁一些,但这是一个次要的风格点。@williampersell你知道,我想我同意。thx,听起来阅读并不是最简单的方式,我真的很喜欢你对IFS的建议
    filename='/tmp/temp.txt'
    while read ; do
      user=$(echo "$REPLY" | cut -d";" -f2)
      address=$(echo "$REPLY" | cut -d";" -f3)
      database=$(echo "$REPLY" | cut -d";" -f4)
      right=$(echo "$REPLY" | cut -d";" -f5)
      ...
    
    while IFS=";" read -r empty user address database right empty; do
        echo "user:$user address:$address database:$database right:$right"
    done < $filename
    
    $ sed 's/;/user: /;s/;/ address: /;s/;/ db: /;s/;/ right: /;s/;//' infile
    user: user1 address: 1.1.1.1 db: DB1 right: SELECT
    user: userX address: 2.2.2.2 db: DB4 right: SELECT