这是我构建的脚本
根据作为参数提供的扩展名,它需要一个文件列表。
然后删除模式00000000之前的所有内容:在这些文件中。
<pre>
,然后删除这五个第一个字符。if [[ $# -eq 0 ]] ; then echo 'Run script as ./hexconv ext' exit 0 fi for file in *.$1 do filename=$(basename $file) extension="${filename##*.}" filename="${filename%.*}" sed -n '/00000000:/,$p' $file | sed '1s/^.....//' | head -n -3 | awk '{print $2" "$3" "$4" "$5" "$6" "$7" "$8" "$9" "$10" "$11" "$12" "$13" "$14" "$15" "$16" "$17}' | xxd -p -r > $filename.jpg done
它也可以按照我的意愿行事,但我怀疑有些东西需要改进,但是唉,我是使用awk和sed的新手。
摘自文件
<th>response-head:</th>
<td>HTTP/1.1 200 OK
Date: Sun, 15 Dec 2013 04:27:04 GMT
Server: PWS/8.0.18
X-Px: ms h0-s34.p6-lhr ( h0-s35.p6-lhr), ht-d h0-s35.p6-lhr.cdngp.net
Etag: "4556354-9fbf8-4e40387aadfc0"
Cache-Control: no-store, no-cache, must-revalidate, post-check=0, pre-check=0, max-age=0
Accept-Ranges: bytes
Content-Length: 654328
Content-Type: image/jpeg
Last-Modified: Thu, 15 Aug 2013 21:55:19 GMT
Pragma: no-cache
</td>
</tr>
</table>
<hr/>
<pre>00000000: ff d8 ff e0 00 10 4a 46 49 46 00 01 01 01 00 48 ......JFIF.....H
00000010: 00 48 00 00 ff e1 00 18 45 78 69 66 00 00 49 49 .H......Exif..II
00000020: 2a 00 08 00 00 00 00 00 00 00 00 00 00 00 ff ed *...............
00000030: 00 48 50 68 74 73 68 70 20 33 2e 30 00 .HPhotoshop 3.0.
00000040: 38 42 49 4d 04 04 00 00 00 00 00 1c 01 5a 00 8BIM..........Z.
00000050: 03 1b 25 47 1c 02 00 00 02 00 02 00 38 42 49 4d ..%G........8BIM
00000060: 04 25 00 00 00 00 00 10 fc e1 89 c8 b7 c9 78 .%.............x
00000070: 34 62 34 07 58 77 eb ff e1 03 a5 68 74 74 70 /4b4.Xw.....http
00000080: 3a 6e 73 2e 61 64 62 65 2e 63 6d ://ns.adobe.com/
00000090: 78 61 70 31 2e 30 00 3c 78 70 61 63 6b xap/1.0/.<?xpack
000000a0: 65 74 20 62 65 67 69 6e 3d 22 ef bb bf 22 20 69 et begin="..." i
000000b0: 64 3d 22 57 35 4d 30 4d 70 43 65 68 69 48 7a 72 d="W5M0MpCehiHzr
000000c0: 65 53 7a 4e 54 63 7a 6b 63 39 64 22 3e 20 3c eSzNTczkc9d"?> <
000000d0: 78 3a 78 6d 70 6d 65 74 61 20 78 6d 6c 6e 73 3a x:xmpmeta xmlns:
000000e0: 78 3d 22 61 64 62 65 3a 6e 73 3a 6d 65 74 61 x="adobe:ns:meta
000000f0: 22 20 78 3a 78 6d 70 74 6b 3d 22 41 64 62 /" x:xmptk="Adob
00000100: 65 20 58 4d 50 20 43 72 65 20 35 2e 30 2d 63 e XMP Core 5.0-c
00000110: 30 36 31 20 36 34 2e 31 34 30 39 34 39 2c 20 32 061 64.140949, 2
00000120: 30 31 30 31 32 30 37 2d 31 30 3a 35 37 3a 010/12/07-10:57:
答案 0 :(得分:1)
虽然@CodeGnome是正确的,而且这可能属于Code Review SE,但无论如何你要去:
将多个 sed
命令组合成一个命令的效率稍高,例如:
sed -n -e 's/^<pre>//' -e '/00000000:/,$p'
我决定收回这一部分,因为我不确定它是更好还是更清楚。您的版本没问题,只有s/^<pre>//
优于s/^.....//
。
在检查发出错误信号的参数数量时使用exit 1
那里for file in *.
是什么?迭代所有以点结尾的文件?错字?
除非您100%确定文件名永远不会包含空格,否则您应该引用它们,但不要引用您不需要的地方,例如:
filename=$(basename "$file") # need to quote
extension=${filename##*.} # no need,
filename=${filename%.*} # no need
sed ... "$file" # need to quote
... | xxd > "$filename".jpg # need to quote
最后一个awk
可以更短,更不容易出错:
... | awk '{printf $2; for (i=3; i<=17; ++i) printf " " $i; print ""}'
看来你想学习。您可能也对这个其他答案感兴趣:What are the rules to write robust shell scripts?
答案 1 :(得分:0)
错误消息应该发送到stderr,不应该硬编码脚本的名称以防以后重命名,并且应该以非零值退出。
if (( ! $# )); then
echo >&2 "Run script as '$0' \$extension"
exit 1
fi
如果您要将then
放在与if
相同的行上,那么您应该将do
放在与for
相同的行上,为了保持一致性:
for file in *.$1; do
使用file
作为全名,使用filename
作为基本名称会让变量名称选择混乱。我会使用basename
作为变量来匹配操作。你需要引用参数扩展:
basename=$(basename "$file")
但是你不需要引用作业的右侧:
extension=${basename##*.}
没有扩展名的文件名部分有时称为root
(在vi和csh :
- 修饰符中,您可以使用:r
)...使用该名称比改变现有变量并重复使用它更容易混淆:
root=${basename%.*}
就实际管道而言,我会重新排序,将head
放在awk
之前,因为sed
和head
都是关于哪些行打印出来并应在awk
之前将其组合在一起,以修改这些选定的行。我还会使用一个循环和printf
来使awk
变得更加狡猾:
sed -n '/0\{8\}:/,$p' "$file" |
head -n -3 |
awk '{ printf "%s", $2; for (f=3;f<=17;++f) { printf " %s", $f }; print "" }' |
xxd -p -r > "$root.jpg"
done