string - 对文本文件中的所有字符进行操作的更快方法
问题描述
我想在一个很长的字符串上执行一个任务,我认为我需要单独对每个字符进行操作。在这样做之前,我首先尝试建立访问所有这些字符所需时间的基线。
我打算使用的输入是一个文本文件,其中一行包含一个由数字组成的单词。
下面的代码是我迄今为止最好的尝试,是否有更快的方法来逐个访问字符串中的所有字符?
function handle_split() {
split=$1
while read -N 1 char; do
:
done
}
while read -N 100000 split; do
((i=i%100)); ((i++==0)) && wait
handle_split $split &
done < "filename.txt"
此行旨在避免同时排队超过 100 个任务
((i=i%100)); ((i++==0)) && wait
拆分的长度是根据输入的已知长度硬编码的,在这种情况下,我使用的是大约十亿个字符的字符串。
顺便说一句,我试图将我的字符串拆分转换为数组以提高性能。
function handle_split() {
split=($@)
for char in ${split[@]}; do
:
done
}
while read -N 100 split; do
arr=($(echo $split | grep -o .))
((i=i%100)); ((i++==0)) && wait
handle_split "${arr[@]}" &
done < "filename.txt"
但是这种使用数组的实现甚至比简单的 for 循环还要慢。
while read -N 1 char; do
:
done < "filename.txt"
解决方案
GNU 或 BSDawk
在这里可能是一个不错的选择:
awk 'BEGIN {FS=""}
{for(i=1;i<=NF;i++) a[$i]++}
END {for(i=0;i<10;i++) for(j=0;j<a[i];j++) printf "%d", i}' file
应该是关于你想要什么。解释:FS=""
在BEGIN
块中意味着文件中的每个单个字符都是一个单独的字段。该{for(i=1;i<=NF;i++) a[$i]++}
块循环遍历所有字段(1 到NF
),并为每个字段递增a
数组的 10 个单元之一。该END
块在 END 处执行,它按数字递增的顺序打印每个数字d
的次数。a[d]
请注意,这不会打印最终的换行符。如果您需要; print ""
在块的末尾添加一个:
END {for(i=0;i<10;i++) for(j=0;j<a[i];j++) printf "%d", i; print ""}
当然,结果是如此多余,以至于您可能更喜欢更紧凑的形式,例如,每个字符一行有两个字段:字符和出现次数:
awk 'BEGIN {FS=""}
{for(i=1;i<=NF;i++) a[$i]++}
END {for(i in a) printf "%s %d\n", i, a[i]}' file
刚刚在具有 1.4GB 输入的 3.6 GHz Intel Core i7 上测试了最后一个:2m38.480s。
推荐阅读
- python - 仅当未在 Python 类中定义时才覆盖使用自变量
- python-3.x - 明智地取出所有类型的电影
- python - 如何根据另一个对象的位置使某物旋转
- char - 乳胶表:在表格单元格中包含“\ n”?
- json - 如何为 Apache Flink 创建自定义 POJO
- android - 关于 Android 的 Firebase 身份验证 SHA1 的问题
- powershell - 任务计划 | 我正在尝试安排一个 .ps1 文件,但每次调度程序运行时都会出现一个弹出窗口“你想如何打开这个文件?”
- python - 如何将一个扩展名的一个目录的所有文件合并到一个文件夹中
- android - Gradle 构建过程失败
- flutter - 地图未更新呈现的有状态子小部件