pax*_*blo 164

可能最有效的方法,如果你使用bashshell(并且你看起来是基于你的评论),则使用参数扩展的子字符串变体:

pax> long="USCAGol.blah.blah.blah"
pax> short="${long:0:2}" ; echo "${short}"
US
Run Code Online (Sandbox Code Playgroud)

这将设置short为前两个字符long.如果long短于两个字符,short则与它相同.

这种shell内方法通常会更好,如果你要做很多事情(如你所提到的那样每报告50,000次),因为没有进程创建开销.所有使用外部程序的解决方案都会遭受这种开销.

如果你还想确保最小的长度,你可以事先用以下方法填写:

pax> long="A"
pax> tmpstr="${long}.."
pax> short="${tmpstr:0:2}" ; echo "${short}"
A.
Run Code Online (Sandbox Code Playgroud)

这将确保长度小于两个字符的任何内容用句点(或其他内容,仅通过更改创建时使用的字符tmpstr)填充在右侧.目前尚不清楚你是否需要这个,但我认为我会把它完整.


话虽如此,有很多方法可以使用外部程序(例如,如果您没有bash可用),其中一些方法是:

short=$(echo "${long}" | cut -c1-2)
short=$(echo "${long}" | head -c2)
short=$(echo "${long}" | awk '{print substr ($0, 0, 2)}'
short=$(echo "${long}" | sed 's/^\(..\).*/\1/')
Run Code Online (Sandbox Code Playgroud)

前两个(cuthead)对于单行字符串是相同的 - 它们基本上只返回前两个字符.它们的不同之处在于cut它将为您提供每行的前两个字符,并head为您提供整个输入的前两个字符

第三个使用awk子字符串函数提取前两个字符,第四个使用sed捕获组(使用()\1)捕获前两个字符并用它们替换整行.它们都相似cut- 它们在输入中传递每行的前两个字符.

如果您确定您的输入是单行,那么这些都无关紧要,它们都具有相同的效果.


enn*_*ler 49

最简单的方法是

${string:position:length}
Run Code Online (Sandbox Code Playgroud)

这哪里提取$length子从$string$position.

这是一个内置的bash,因此不需要awk或sed.


Pau*_*ce. 31

你已经得到了一些很好的答案,我会用猛砸去内建自己,但既然你问sedawk和(几乎是基于他们)没有其他人提供的解决方案,我给你这些报价:

echo "USCAGoleta9311734.5021-120.1287855805" | awk '{print substr($0,0,2)}'
Run Code Online (Sandbox Code Playgroud)

echo "USCAGoleta9311734.5021-120.1287855805" | sed 's/\(^..\).*/\1/'
Run Code Online (Sandbox Code Playgroud)

这个awk应该是相当明显的,但这里有一个解释sed:

  • 替换"s /"
  • 从"^"行开头的任何字符".."中的两个字符串"()",后跟任何字符"." 重复零次或多次"*"(需要反斜杠来逃避一些特殊字符)
  • 通过"/"第一个(也是唯一的,在这种情况下)组的内容(这里反斜杠是一个特殊的转义,指的是匹配的子表达式)
  • 完成"/"


Jua*_*uan 11

如果您想使用 shell 脚本而不依赖于非 posix 扩展(例如所谓的 bashism),您可以使用不需要 fork 外部工具的技术,例如 grep、sed、cut、awk 等,然后使你的脚本效率降低。也许效率和 posix 可移植性在您的用例中并不重要。但如果是这样(或者只是作为一个好习惯),您可以使用以下参数扩展选项方法来提取 shell 变量的前两个字符:

$ sh -c 'var=abcde; echo "${var%${var#??}}"'
ab
Run Code Online (Sandbox Code Playgroud)

这使用“最小前缀”参数扩展来删除前两个字符(这是部分${var#??}),然后使用“最小后缀”参数扩展(部分${var%)来从原始字符串中删除除前两个字符之外的所有字符串价值。

之前在“Shell = 检查变量是否以 # 开头”问题的答案中描述了此方法。该答案还描述了几种类似的参数扩展方法,这些方法可以在与此处适用于原始问题的方法略有不同的上下文中使用。

  • 最佳答案,应该在最上面。没有叉子,没有bashisms。甚至可以与 dash 等小 shell 一起使用。 (2认同)
  • 我喜欢尽可能避免羞怯。 (2认同)

Dom*_*ell 7

如果你在bash,你可以说:

bash-3.2$ var=abcd
bash-3.2$ echo ${var:0:2}
ab
Run Code Online (Sandbox Code Playgroud)

这可能正是你所需要的......


Ami*_*ler 7

只是grep:

echo 'abcdef' | grep -Po "^.."        # ab
Run Code Online (Sandbox Code Playgroud)


bsc*_*ter 6

您可以使用printf

$ original='USCAGoleta9311734.5021-120.1287855805'
$ printf '%-.2s' "$original"
US
Run Code Online (Sandbox Code Playgroud)


小智 5

colrm — 从文件中删除列

要保留前两个字符,只需删除从 3 开始的列

cat file | colrm 3
Run Code Online (Sandbox Code Playgroud)