在printf中填充字符
我正在编写一个bash shell脚本来显示一个进程是否正在运行。
到目前为止,我在这里。
printf "%-50s %s\n" $PROC_NAME [UP] 这给了我一个输出,如:
 JBoss [DOWN] GlassFish [UP] verylongprocessname [UP] 
我想用“ – ”或“*”填充两个字段之间的空白,以使其更具可读性。 我怎样才能做到这一点,而不会干扰领域的一致?
我想要的输出是:
 JBoss ------------------------------------------- [DOWN] GlassFish --------------------------------------- [UP] verylongprocessname ----------------------------- [UP] 
	
纯Bash,没有外部公用事业
这个演示做了充分的理由,但是如果你想要粗糙的线条,你可以省略减去第二个string的长度。
 pad=$(printf '%0.1s' "-"{1..60}) padlength=40 string2='bbbbbbb' for string1 in a aa aaaa aaaaaaaa do printf '%s' "$string1" printf '%*.*s' 0 $((padlength - ${#string1} - ${#string2} )) "$pad" printf '%s\n' "$string2" string2=${string2:1} done 
不幸的是,焊盘string的长度必须被硬编码,但是焊盘长度可以是一个variables,如图所示。
输出:
 a--------------------------------bbbbbbb aa--------------------------------bbbbbb aaaa-------------------------------bbbbb aaaaaaaa----------------------------bbbb 
不减去第二个string的长度:
 a---------------------------------------bbbbbbb aa--------------------------------------bbbbbb aaaa------------------------------------bbbbb aaaaaaaa--------------------------------bbbb 
 第一行可能是等效的(类似于sprintf ): 
 printf -v pad '%0.1s' "-"{1..60} 
如果您喜欢,您可以在一行上完成打印:
 printf '%s%*.*s%s\n' "$string1" 0 $((padlength - ${#string1} - ${#string2} )) "$pad" "$string2" 
纯粹的打击。 使用'PROC_NAME'的值的长度作为固定string'line'的偏移量:
 line='----------------------------------------' PROC_NAME='abc' printf "%s %s [UP]\n" $PROC_NAME "${line:${#PROC_NAME}}" PROC_NAME='abcdef' printf "%s %s [UP]\n" $PROC_NAME "${line:${#PROC_NAME}}" 
这给了
 abc ------------------------------------- [UP] abcdef ---------------------------------- [UP] 
琐碎(但工作)的解决scheme:
 echo -e "---------------------------- [UP]\r$PROC_NAME " 
 echo -n "$PROC_NAME $(printf '\055%.0s' {1..40})" | head -c 40 ; echo -n " [UP]" 
说明:
-   printf '\055%.0s' {1..40}– 创build40个破折号
 (破折号被解释为选项,所以使用转义ascii代码)
-   "$PROC_NAME ..."– 连接$ PROC_NAME和破折号
-  | head -c 40| head -c 40– 修剪string到前40个字符
 没有办法使用printf填充空格而不是空格。 你可以使用sed : 
 printf "%-50s@%s\n" $PROC_NAME [UP] | sed -e 's/ /-/g' -e 's/@/ /' -e 's/-/ /' 
这个更简单,不需要外部命令。
 $ PROC_NAME="JBoss" $ PROC_STATUS="UP" $ printf "%-.20s [%s]\n" "${PROC_NAME}................................" "$PROC_STATUS" JBoss............... [UP] 
我认为这是最简单的解决scheme。 纯壳build立,没有内联math。 它借鉴了以前的答案。
只是子string和$ {#…}元variables。
 A="[>---------------------<]"; # Strip excess padding from the right # B="A very long header"; echo "${A:0:-${#B}} $B" B="shrt hdr" ; echo "${A:0:-${#B}} $B" 
产生
 [>----- A very long header [>--------------- shrt hdr # Strip excess padding from the left # B="A very long header"; echo "${A:${#B}} $B" B="shrt hdr" ; echo "${A:${#B}} $B" 
产生
 -----<] A very long header ---------------<] shrt hdr 
  只使用echo 
  @Dennis Williamson的工作人员工作得很好,除了我试图用echo来做这件事。 回声允许输出特定颜色的charcacters。 使用printf将删除该着色并打印不可读的字符。 这里是echo唯一的select: 
 string1=abc string2=123456 echo -en "$string1 " for ((i=0; i< (25 - ${#string1}); i++)){ echo -n "-"; } echo -e " $string2" 
输出:
 abc ---------------------- 123456 
 当然,您可以使用@Dennis Williamson提出的所有变体,无论您想要将右部分左alignment还是右alignment(用25 - ${#string1}replace25 - ${#string1} - ${#string2}等等… 
这是另外一个:
 $ { echo JBoss DOWN; echo GlassFish UP; } | while read PROC STATUS; do echo -n "$PROC "; printf "%$((48-${#PROC}))s " | tr ' ' -; echo " [$STATUS]"; done JBoss -------------------------------------------- [DOWN] GlassFish ---------------------------------------- [UP] 
 如果你在一些固定的列号结束填充字符,那么你可以overpad和cut长度: 
 # Previously defined: # PROC_NAME # PROC_STATUS PAD="--------------------------------------------------" LINE=$(printf "%s %s" "$PROC_NAME" "$PAD" | cut -c 1-${#PAD}) printf "%s %s\n" "$LINE" "$PROC_STATUS"