我有一些很长的汉字字符串,但为了这个问题,我们假设它们是:
啊爱好情人心安静排全装按照八把握爸吧白菜酒色夭百班长板
和
阿姨啊挨打矮小爱国护安检慰置岸边上按摩时案子暗示巴士拔
第一个字符串列出了所有“简单”的汉字。第二个字符串列出了所有“易”和“中”汉字,但我只想要“中”汉字:我想从第二个字符串中删除“易”字符。
例如,编辑后,第二个字符串将不包含“啊”或“爱”(可能还有更多删除),因为它们都出现在第一个字符串中。
问题: 当字符串A中出现中文字符时,如何从字符串B中删除它们,同时保留顺序?
我觉得这应该可以用awk
or解决sed
或者其他东西来解决;我不介意。看起来我可以将这些字符串转换为两个文本文件,并使用中的任何一个命令如何从另一个文件A中删除文件B上出现的行? 但是,我宁愿在不创建辅助文件的情况下执行此操作。
保留字符串中字符的顺序也很重要。
答案1
在允许语法${parameter/pattern/string}
(ksh、bash、zsh)的 shell 中,您可以执行以下操作:
$ easy='啊爱好情人心安静排全装按照八把握爸吧白菜酒色夭百班长板'
$ intermediate='阿姨啊挨打矮小爱国护安检慰置岸边上按摩时案子暗示巴士拔'
$ echo "${intermediate//[$easy]/}"
阿姨挨打矮小国护检慰置岸边上摩时案子暗示巴士拔
这是基于类似正则表达式的字符选择[…]
。其中也存在的
所有单个字符都将被删除。intermediate
easy
独立于 shell 的等效项可能是:
$ echo "$intermediate" | sed 's/['"$easy"']//g'
阿姨挨打矮小国护检慰置岸边上摩时案子暗示巴士拔
答案2
使用 Raku(née Perl6)
Raku 的设计初衷就是为了优雅地处理 Unicode。下面每对的第一个示例通常来自 Raku 文档;每对的第二个例子适用于解决您的特定中文字符串:
$ echo "a123b123c" | raku -pe 'tr:d/123//;'
abc
$ echo "阿姨啊挨打矮小爱国护安检慰置岸边上按摩时案子暗示巴士拔" | raku -pe 'tr:d/啊爱好情人心安静排全装按照八把握爸吧白菜酒色夭百班长板//;'
阿姨挨打矮小国护检慰置岸边上摩时案子暗示巴士拔
或者
$ echo "a123b123c" | raku -pe '.=trans("123" => "");'
abc
$ echo "阿姨啊挨打矮小爱国护安检慰置岸边上按摩时案子暗示巴士拔" | raku -pe '.=trans("啊爱好情人心安静排全装按照八把握爸吧白菜酒色夭百班长板" => "");'
阿姨挨打矮小国护检慰置岸边上摩时案子暗示巴士拔
命令-pe
行标志指示 Raku 按行获取输入并自动打印返回值。tr///
操作员和例程之间存在细微差别trans()
。下面的文档,HTH。
https://docs.raku.org/language/operators#tr///_in-place_transliteration
https://docs.raku.org/routine/trans
https://raku.org/
答案3
我想到了!它可能不是最好的解决方案,但它有效:
echo 阿姨啊挨打矮小爱国护安检慰置岸边上按摩时案子暗示巴士拔 | sed -e "s/.\{1\}/&\n/g" | awk -v pat="啊爱好情人心安静排全装按照八把握爸吧白菜酒色夭百班长板" 'pat ~ $0' | tr -d '\n'
解释:
echo 阿姨啊挨打矮小爱国护安检慰置岸边上按摩时案子暗示巴士拔
是一种将第二个字符串作为输入进行管道传输的方法sed -e "s/.\{1\}/&\n/g"
在每个字符后添加换行符awk -v pat="啊爱好情人心安静排全装按照八把握爸吧白菜酒色夭百班长板" 'pat !~ $0'
pat
仅打印(第一个字符串)中未出现的字符tr -d '\n'
摆脱所有换行符
它给出了输出
阿姨挨打矮小国护检慰置岸边上摩时案子暗示巴士拔
并删除字符“啊”、“爱”、“安”、“按”。