带有变量和行号限制的Sed
我有以下文件:带有变量和行号限制的Sed,sed,Sed,我有以下文件: <CamcorderProfiles cameraId="0"> <EncoderProfile quality="720p" fileFormat="mp4" duration="30"> <Video codec="h264" bitRate="8000000" width="1280" height="720"
<CamcorderProfiles cameraId="0">
<EncoderProfile quality="720p" fileFormat="mp4" duration="30">
<Video codec="h264"
bitRate="8000000"
width="1280"
height="720"
frameRate="30" />
<Audio codec="aac"
bitRate="96000"
sampleRate="48000"
channels="1" />
</EncoderProfile>
<EncoderProfile quality="1080p" fileFormat="mp4" duration="30">
<Video codec="h264"
bitRate="12000000"
width="1920"
height="1080"
frameRate="30" />
<Audio codec="aac"
bitRate="96000"
sampleRate="48000"
channels="1" />
</EncoderProfile>
</CamcorderProfiles>
<CamcorderProfiles cameraId="1">
<EncoderProfile quality="720p" fileFormat="mp4" duration="30">
<Video codec="h264"
bitRate="8000000"
width="1280"
height="720"
frameRate="30" />
<Audio codec="aac"
bitRate="96000"
sampleRate="48000"
channels="1" />
</EncoderProfile>
<EncoderProfile quality="1080p" fileFormat="mp4" duration="30">
<Video codec="h264"
bitRate="12000000"
width="1920"
height="1080"
frameRate="30" />
<Audio codec="aac"
bitRate="96000"
sampleRate="48000"
channels="1" />
</EncoderProfile>
</CamcorderProfiles>
如果我将代码的第一行改为cameraId=“1”
,那么对于这种情况,我确实会得到正确的结果
camerastart = 31
cameraend = 57
camera1080pstart = 45
如果我更改代码,使前两个变量硬编码,我会得到17
camera1080pstart的正确输出
camerastart="3"
cameraend="29"
camera1080pstart=$(sed -n $camerastart','$cameraend' {/<EncoderProfile quality="1080p" fileFormat="mp4" duration="30">/=}' $file)
camerastart=“3”
cameraend=“29”
camera1080pstart=$(sed-n$camerastart','$cameraend'{/=}'$文件)
有人知道发生了什么吗?这里有一个脚本,可以找到并打印您要更改的行: $cat tst.awk
BEGIN{ FS = "\"" }
/<CamcorderProfiles cameraId=/ { cameraId = $2 }
/<EncoderProfile quality=/ { quality = $2 }
/bitRate="12000000"/ {
if ( (cameraId == "0") && (quality == "1080p") ) {
print NR, "this is the line I want to change:"
print
}
}
$ awk -f tst.awk file
17 this is the line I want to change:
bitRate="12000000"
下面是一个脚本,它将查找并打印要更改的行: $cat tst.awk
BEGIN{ FS = "\"" }
/<CamcorderProfiles cameraId=/ { cameraId = $2 }
/<EncoderProfile quality=/ { quality = $2 }
/bitRate="12000000"/ {
if ( (cameraId == "0") && (quality == "1080p") ) {
print NR, "this is the line I want to change:"
print
}
}
$ awk -f tst.awk file
17 this is the line I want to change:
bitRate="12000000"
将第二个命令更改为:
cameraend=$(sed -n $camerastart',$ {/<\/CamcorderProfiles>/=}' $file | head -1)
cameraend=$(sed-n$camerastart',${/=}'$file | head-1)
因为它返回多个行号。但是,这可能不是解决此特定问题的最佳方法。将第二个命令更改为:
cameraend=$(sed -n $camerastart',$ {/<\/CamcorderProfiles>/=}' $file | head -1)
cameraend=$(sed-n$camerastart',${/=}'$file | head-1)
因为它返回多个行号。但是,这可能不是解决这个特定问题的最佳方法。对我有效的解决方案是:
camerastart=$(sed -n '{/<CamcorderProfiles cameraId="0">/=}' $file | head -1)
cameraend=$(sed -n $camerastart',$ {/<\/CamcorderProfiles>/=}' $file | head -1)
camera1080pstart=$(sed -n $camerastart','$cameraend' {/<EncoderProfile quality="1080p" fileFormat="mp4" duration="30">/=}' $file | head -1)
camerastart=$(sed-n'{/=}'$file | head-1)
cameraend=$(sed-n$camerastart',${/=}'$file | head-1)
camera1080pstart=$(sed-n$camerastart','$cameraend'{/=}'$file | head-1)
对我有效的解决方案是:
camerastart=$(sed -n '{/<CamcorderProfiles cameraId="0">/=}' $file | head -1)
cameraend=$(sed -n $camerastart',$ {/<\/CamcorderProfiles>/=}' $file | head -1)
camera1080pstart=$(sed -n $camerastart','$cameraend' {/<EncoderProfile quality="1080p" fileFormat="mp4" duration="30">/=}' $file | head -1)
camerastart=$(sed-n'{/=}'$file | head-1)
cameraend=$(sed-n$camerastart',${/=}'$file | head-1)
camera1080pstart=$(sed-n$camerastart','$cameraend'{/=}'$file | head-1)
是的,您使用了错误的工具。sed是一个很好的工具,用于在单行上进行简单替换,对于任何其他文本处理任务,您都应该使用awk。告诉我们您正在尝试做什么,并发布一些与示例输入匹配的预期输出,有人会告诉您正确的方法。我要做的是编辑xml文件的特定行。例如,将EncoderProfile quality=“1080p”标记和cameraId=“0”标记内的bitRate=“12000000”行更改为其他内容。不知何故,我需要深入研究多个标记层,以便在正确的标记中更改行。我发布了一个小的awk脚本,让您开始,但您需要告诉我们您希望以何种方式更改找到的行,并提供其他信息以进一步。是的,您使用了错误的工具。sed是一个很好的工具,用于在单行上进行简单替换,对于任何其他文本处理任务,您都应该使用awk。告诉我们您正在尝试做什么,并发布一些与示例输入匹配的预期输出,有人会告诉您正确的方法。我要做的是编辑xml文件的特定行。例如,将EncoderProfile quality=“1080p”标记和cameraId=“0”标记内的bitRate=“12000000”行更改为其他内容。不知何故,我需要深入研究多个标记层,以便在正确的标记中更改行。我发布了一个小的awk脚本,让您开始,但您需要告诉我们您希望以何种方式更改找到的行,并提供其他信息以进一步。我尝试在变量中获取第17行的原因是,这样我可以运行sed-i'17 s/12000000/20000000/”文件
在该行。我可以在您的脚本中正确地执行此操作吗?当然可以,但是当您已经在处理目标行时,不需要获取行号。我现在将更新脚本,将12000000更改为20000000。我尝试在变量中获取第17行的原因是,我可以在该行上运行类似于sed-I'17 s/12000000/20000000/”的文件。我可以在您的脚本中正确地执行此操作吗?当然可以,但是当您已经在处理目标行时,不需要获取行号。我现在将更新脚本,将12000000更改为20000000。您可能了解一些情况。那有什么用?仅返回第一个实例?是的,head-1
返回其输入的第一行,因此您仅获得第一个实例。因此,如果您尝试迭代所有实例,您可以使用grep-c
和head
。您是个天才。成功了!我想最好是把head-1
放在它们上面,以防存在多个实例。你可能会发现一些东西。那有什么用?仅返回第一个实例?是的,head-1
返回其输入的第一行,因此您仅获得第一个实例。因此,如果您尝试迭代所有实例,您可以使用grep-c
和head
。您是个天才。成功了!我想最好是在所有的上面都加上head-1
,以防存在多个实例。
camerastart=$(sed -n '{/<CamcorderProfiles cameraId="0">/=}' $file | head -1)
cameraend=$(sed -n $camerastart',$ {/<\/CamcorderProfiles>/=}' $file | head -1)
camera1080pstart=$(sed -n $camerastart','$cameraend' {/<EncoderProfile quality="1080p" fileFormat="mp4" duration="30">/=}' $file | head -1)