【问题标题】:Not able to perform multiple sed operations at a time无法一次执行多个 sed 操作
【发布时间】:2014-07-26 15:51:27
【问题描述】:

您好,我需要一次执行多个 sed 操作,然后将输出刷新到文件中。 我有一个 .dat 文件,其数据如下

indicator.dat

Air_Ind - A.Air_Ind Air_Ind - 0000 - 00- 00 Rpting_Ind - Dstbr_Id 为 Null 然后为 'N' 否则为 'Y' End Rpting_Ind - 0000 - 00 - 00 的情况 纬度,经度 - A.Store_Latitude 纬度,A.Store_Longitude 经度 - 0000- 00- 00 合并(Pm_Cig_Direct_Ind,'')-合并(Direct_Acct_Ind,'')- 0004 - 01- 01 合并(Pm_Mst_Direct_Ind,'')-合并(Direct_Acct_Ind,'')- 0004 - 02 - 02 合并(Pm_Snus_Direct_Ind,'')-合并(Direct_Acct_Ind,'')- 0004 - 01 - 02 合并(Pm_Snuf_Direct_Ind,'')-合并(Direct_Acct_Ind,'')- 0004 - 04- 02 合并(Jmc_Cgr_Direct_Ind,'')-合并(Direct_Acct_Ind,'')- 2000 - 02 - 01 合并(Usst_Mst_Direct_Ind,'')-合并(Direct_Acct_Ind,'')- 1070- 02- 02 合并(Usst_Snus_Direct_Ind,'') - 合并(Direct_Acct_Ind,'') - 1070 - 01 - 02 合并(Usst_Snuf_Direct_Ind,'') - 合并(Direct_Acct_Ind,'') - 1070 - 04 - 02

现在我正在尝试替换名为indicator.sql 的文件中定义的参数并将输出刷新到文件中

indicator_s.sql:

    Select A.Location_Id,

 param1

From Edw.Location A

--1Left Outer  Join

--1(

--1 Select

--1 Location_Id,

--1 Direct_Acct_Ind

--1 From Edw.Location_Bcbc D

--1 Where Company_Cd = 'param2'

--1 And Prod_Type_Cd = 'param3'

--1 And Prod_Catg_Cd = 'param4'

--1 ) A

--1 On L.Location_Id = A.Location_Id

Inner Join  

Mim.Mdm_Xref_Distributor D

On D.Src_Dstbr_Id=A.Location_Id

Where Sdw_Exclude_Ind='N' And Dstrb_Cd='Us'

任何时候都不会进入else块

#!/bin/sh
rm ./Source_tmp.sql
touch ./Source_tmp.sql
while read line
do
MIM=`echo $line | cut -d " " -f1 `
EDW=`echo $line | cut -d "-" -f2 `
Company_Cd=`echo $line | cut -d "-" -f3 `
Prod_Type_Cd=`echo $line | cut -d "-" -f4 `
Prod_Catg_Cd=`echo $line | cut -d "-" -f5 `
echo "Select top 10 * from (" >> ./Source_tmp.sql ;
sed "s/Param1/$MIM/g" indicator.sql >> Source_tmp.sql;

echo "minus">> Source_tmp.sql;



if [ "$MIM"="Air_Ind " ] || [ "$MIM"="Rpting_Ind " ] || [ "$MIM"="Latitude,Longitude " ]

then


sed "s/param1/$EDW/g" indicator_s.sql >> Source_tmp.sql

else



sed -e "s/--1/' '/g" -e  "s/param1/$EDW/g" -e "s/param2/$Company_Cd/g" -e "s/param3/$Prod_Type_Cd/g" -e "s/param4/$Prod_Catg_Cd/g"  ./indicator_s.sql >> ./Source_tmp.sql



fi

done <indicator.dat

输出应该像我定义的 param1 和 param2 等值应该从指标 .dat 文件中替换,并且注释行需要在 else 块中取消注释 请帮助我

【问题讨论】:

  • 我读到:“我不知道为什么 sed 不能在 ksh 的 else 块中工作” 但在你的脚本中,shebang 是#!/bin/sh。请修正您的问题/示例/标签,以便澄清您是否需要 bashshksh 答案。
  • UNIX shell 是一个调用工具的环境。操作文本文件内容的标准 UNIX 工具是 awk。您应该编写一个 awk 脚本来完成所有操作,然后从您喜欢的任何 shell 中调用它。结果将比你可以用 shell、sed、cut 和其他命令的混合物来做的任何东西都更简洁和健壮。只需清楚地发布 1) indicator.dat、2) indicator.sql 和 3) 预期工具输出的示例,我们就可以为您提供帮助。我保证你会比你现在尝试做的更快乐。
  • indicator.sql中每个数据行之间真的有空行吗?
  • no Ed 之间没有空行。

标签: sed ksh


【解决方案1】:

据我所知,sed 命令“正在运行”。但它不会产生预期的输出。我猜。给出一些输出示例:

[...]
' ' Where Company_Cd = ' 0000 '

' ' And Prod_Type_Cd = ' 00 '

' ' And Prod_Catg_Cd = ' 00'
[...]

显然,您在行首有额外的引号,并且在您的值周围有额外的间距。

这会解决您的问题吗:

#!/bin/bash

[...]

MIM=`echo -n $line | cut -d " " -f1 `
EDW=`echo -n $line | cut -d "-" -f2 `
Company_Cd=`echo -n $line | cut -d "-" -f3 `
Prod_Type_Cd=`echo -n $line | cut -d "-" -f4 `
Prod_Catg_Cd=`echo -n $line | cut -d "-" -f5 `

# Trim spaces as you "cut" on "-", keeping extra spaces arround
shopt -s extglob
EDW=${EDW%%+([[:space:]])}; EDW=${EDW##+([[:space:]])};
Company_Cd=${Company_Cd%%+([[:space:]])}; Company_Cd=${Company_Cd##+([[:space:]])};
Prod_Type_Cd=${Prod_Type_Cd%%+([[:space:]])}; Prod_Type_Cd=${Prod_Type_Cd##+([[:space:]])};
Prod_Catg_Cd=${Prod_Catg_Cd%%+([[:space:]])}; Prod_Catg_Cd=${Prod_Catg_Cd##+([[:space:]])};

[...]

# Fix "sed" in your "else" clause by removing extra single quotes
sed -e "s/--1/ /g" -e  "s/param1/$EDW/g" -e "s/param2/$Company_Cd/g" -e "s/param3/$Prod_Type_Cd/g" -e "s/param4/$Prod_Catg_Cd/g"  ./indicator_s.sql >> ./Source_tmp.sql

现在生成更有效的 SQL:

  [...]
  Where Company_Cd = '0000'

  And Prod_Type_Cd = '00'

  And Prod_Catg_Cd = '00'
  [...]

话虽如此,这主要是一些 hacks 来修复(一些?)您在脚本中可能遇到的各种问题。但整个事情似乎有点做作。并且脆弱。例如,如果任何替换字符串包含&amp;,它将中断。这里是龙。

【讨论】:

  • 它根本没有被替换。那就是问题所在 。即使有多余的空间也没关系
  • 如果我注释掉 if 块和 else 否则它不会从 if 块中出来,如果 sed 正在工作,if 块是否有任何问题。就像我错过了任何将其修复为 if 块的逻辑缺陷
【解决方案2】:

鉴于到目前为止您只发布了一个脚本,它不会产生您想要的任何输出并且您还没有发布您想要的输出,因此不可能告诉您想要脚本做什么,但让我们从这个开始您可以更新您的问题以显示预期输出并阐明您的要求:

$ cat tst.awk
BEGIN{ FS="-" }
NR==FNR { template = (template ? template ORS : "") $0; next }
{
    split($0,arr,/ /)
    MIM = arr[1]
    EDW = $1
    Company_Cd = $3
    Prod_Type_Cd = $4
    Prod_Catg_Cd = $5

    $0 = "Select top 10 * from (\n" template

    gsub(/Param1/,MIM "\nminus")
    gsub(/param1/,EDW)

    if ( MIM !~ /^Air_Ind|Rpting_Ind|Latitude,Longitude/ ) {
        gsub(/--1/," ")
        gsub(/param2/,Company_Cd)
        gsub(/param3/,Prod_Type_Cd)
        gsub(/param4/,Prod_Catg_Cd)
    }

    print
}

.

$ awk -f tst.awk indicator.sql indicator.dat
Select top 10 * from (
Select A.Id,

 Air_Ind
minus

From Location A

--1Left Outer  Join

--1(

--1 Select

--1 Location_Id,

--1 Direct_Acct_Ind

--1 From Location_Bcbc D

--1 Where Company_Cd = 'param2'

--1 And Prod_Type_Cd = 'param3'

--1 And Prod_Catg_Cd = 'param4'

--1 ) A
Select top 10 * from (
Select A.Id,

 Rpting_Ind
minus

From Location A

--1Left Outer  Join

--1(

--1 Select

--1 Location_Id,

--1 Direct_Acct_Ind

--1 From Location_Bcbc D

--1 Where Company_Cd = 'param2'

--1 And Prod_Type_Cd = 'param3'

--1 And Prod_Catg_Cd = 'param4'

--1 ) A

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-07-13
    • 2017-01-15
    • 1970-01-01
    • 1970-01-01
    • 2017-06-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多