performance - 使用内置函数来增强性能是否会因无故使用子 shell 而被抵消?

标签 performance shell subshell gnu-coreutils

我正在编写一个脚本,需要确保字符串包含逗号。如果没有,我需要脚本退出。考虑下面的内容,我的目的是仅使用内置函数来提高性能:

#!/bin/sh

check_for_commas='This string must contain a comma'

comma_found='0'
iterate_through_string="$check_for_commas"
while [ -n "$iterate_through_string" ]; do
    char="$(printf '%.1s' "$iterate_through_string")"

    if [ "$char" = ',' ]; then
        comma_found='1'
        break
    fi

    iterate_through_string="${iterate_through_string#?}"
done

if [ "$comma_found" != '1' ]; then
    echo 'Your string does not contain a comma. Exiting...'
    exit
else
    echo 'Found a comma in the string. Script can continue...'
fi

我在此脚本中使用命令替换,它会为其迭代的每个字符生成一个子 shell。与此比较:

#!/bin/sh

check_for_commas='This string must contain a comma'

if [ "$(echo "$check_for_commas" | grep -q -F ','; echo "$?")" = '1' ]; then   
    echo 'Your string does not contain a comma. Exiting...'
    exit
else
    echo 'Found a comma in the string. Script can continue...'
fi

我显然不介意做一些额外的工作来挤出额外的性能。但我担心使用如此多的子 shell 已经违背了我最初的意图。

当无缘无故地使用子shell时,我对仅使用内置函数来提高性能的追求是否变得毫无用处?

最佳答案

命令替换,如$(printf ...),确实很昂贵——并且您在这里所做的事情不需要它们

case $check_for_commas in
  *,*) echo "Found a comma in the string";;
  *)   echo "No commas present; exiting"; exit 1;;
esac

在更一般的情况下 - 单独的 fork() 的成本低于 fork()/execve() 对,因此使用单个子 shell 更便宜比单个外部命令调用更有效;但是,如果您将生成多个子 shell 的循环与单个外部命令调用进行比较,哪个更便宜取决于您的循环将迭代多少次(以及这些东西在您的操作系统上的成本有多大—— fork 传统上是额外的)例如,在 Windows 上价格昂贵),并且是一项事实密集型调查。 :)

(谈到最初提出的代码 - 请注意,ksh93 将在特定的 var=$(printf ...) 情况下优化掉 fork;相比之下,在 bash 中,需要使用 printf -v var ... 才能获得相同的效果)。

关于performance - 使用内置函数来增强性能是否会因无故使用子 shell 而被抵消?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49703261/

相关文章:

shell - 如何在每次不输入密码的情况下 curl 多个 PUT/DELETE 请求

r - 从 R 中调用 bash

bash - 在 Bash PS1 提示符中动态更改主机名

jQuery 选择器性能 : a curious case

c++ - DLL函数调用的开销

linux - 从终端在 linux 的所有 makefile 中搜索一个单词

bash - 从管道读取的 while 读取循环后变量被重置

java - 如何测量 Storm 拓扑中的延迟和吞吐量

wcf - 在 .net/WCF 中检测连接速度/带宽

amazon-web-services - AWS RDS 连接字符串