जवाबों:
अधिक सामान्य समाधान होने के लिए अद्यतित उत्तर। यह भी देखना नीचे मेरी एक और जवाब केवल खोल ब्रेस विस्तार और का उपयोग कर pritnf।
$ str='Hello World!'
$ sed -r ':loop; s/ (=*):$/\1=:/; t loop' <<< "$(printf '%-20s:\n' "$str" )"
Hello World!========:
यह काम किस प्रकार करता है?
यह (=*):$/एक स्थान, एक-या-अधिक को कैप्चर करता है जो इसके इनपुट के अंत में =एक बृहदान्त्र द्वारा पीछा करता है :; हम =एक समूह मैच के रूप में सेट करते हैं और \1इसका बैक-रेफरेंस होगा।
जब :loopहमने एक लेबल को परिभाषित किया है loopऔर उसके साथ t loopउस लेबल पर कूद जाएगा जब एक s/ (=*):$/\1=:/सफल प्रतिस्थापन किया है;
के साथ प्रतिस्थापन भाग में \1=:, यह हमेशा =एस की संख्या को बढ़ाएगा और स्ट्रिंग के अंत में बृहदान्त्र को वापस कर देगा।
filler='===================='
string='foo'
printf '%s\n' "$string${filler:${#string}}"
देता है
foo=================
${#string} मूल्य की लंबाई है $string , और ${filler:${#string}}की-स्ट्रिंग है $fillerऑफसेट से ${#string}बाद।
आउटपुट की कुल चौड़ाई अधिकतम चौड़ाई की होगी $filler या उससे अधिक होगी $string।
भराव स्ट्रिंग कर सकते हैं, सिस्टम पर jot गतिशील रूप से उपयोग करके बनाया जा सकता है
filler=$( jot -s '' -c 16 '=' '=' )
( =एक पंक्ति में 16 के लिए )। GNU सिस्टम इस्तेमाल कर सकते हैंseq :
filler=$( seq -s '=' 1 16 | tr -dc '=' )
अन्य प्रणालियाँ स्ट्रिंग को गतिशील रूप से बनाने के लिए पर्ल या किसी अन्य तेज़ तरीके का उपयोग कर सकती हैं।
printf+ ब्रेस विस्तार के साथ आप इसे कैसे करेंगे bash?
printf "%.20s:\n\n" "$str========================="
जहां %.20sस्ट्रिंग छंटनी प्रारूप है
इसे करने का एक तरीका:
printf "====================:\r%s\n\n" 'hello world!!'
====================\rhello world, जो एक मुद्दा हो सकता है अगर ओपी को इसे स्टोर करने की जरूरत है और न ही इसे स्क्रीन पर प्रिंट करें।
echo -e '=================\rHello World!!', लेकिन @terdon के रूप में एक ही मुद्दा है कि बताया।
echoसमर्थन करता है -e। कई कारणों printfसे लगभग हमेशा बेहतर होता echoहै।
एक पर्ल दृष्टिकोण:
$ perl -le '$k="hello world!!"; while(length($k)<20){$k.="=";} print "$k\n"'
hello world!!=======
या, बेहतर, @SatoKatsura ने टिप्पणियों में बताया:
perl -le '$k = "hello world!!"; print $k, "=" x (20-length $k), "\n"'
यदि आपको UTF मल्टी-बाइट वर्णों का समर्थन करने की आवश्यकता है, तो उपयोग करें:
PERL_UNICODE='AS' perl -le '$k = "hello world!!"; print $k, "=" x (20-length $k), "\n"'
शेल में एक ही विचार:
v='hello world!!'; while [ ${#v} -lt 20 ]; do v="$v""="; done; printf '%s\n\n' "$v"
perl -le '$k = "hello world!!"; print $k, "=" x (20-length $k), "\n"'। हालाँकि, यह (और अब तक पोस्ट किए गए अन्य सभी समाधान) तोड़ता है यदि मल्टी-बाइट वर्ण शामिल हैं।
perl6मल्टी-बाइट पात्रों के साथ भी इसे सही तरीके से करने का एक तरीका हो सकता है। लेकिन दूसरी तरफ perl6इतने तरीकों से गुस्सा आ रहा है।
PERL_UNICODE='AS'। उदाहरण के लिए: printf '%s' nóóös | perl -nle 'print length($_)'प्रिंट 8 ("गलत") जबकि printf '%s' nóóös | PERL_UNICODE='AS' perl -nle 'print length($_)'प्रिंट 5 ("सही")।
एक अन्य तरीका केवल printfकमांड का उपयोग कर रहा है और चरित्र पैडिंग पैटर्न को पहले उत्पन्न करता है Shell Brace Expansion(आप एक संख्या ting स्वरूपण क्षेत्र जिसे आप प्रिंट करना चाहते हैं, के साथ समाप्त कर सकते हैं {1..end}) और इसके केवल पहले वर्ण को प्राप्त करें %.1sजो =s है और फिर केवल पहले 20 अक्षरों की लंबाई प्रिंट करें उस का क्षेत्र %.20s। यह दोहराए जाने वाले अक्षरों / शब्दों के बजाय उन्हें नक़ल करने के लिए बेहतर तरीका है।
printf '%.20s:\n' "$str$(printf '%.1s' ={1..20})"
Hello World!!=======:
स्पष्टीकरण:
ब्रेस विस्तार के रूप में आम तौर पर , {1..20}यदि हम इसे प्रिंट करते हैं तो शेल विस्तार के रूप में।
printf '%s ' {1..20}
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
तो इसके साथ एक समान चिह्न जोड़ने के साथ ={1..20}, शेल निम्नलिखित के रूप में विस्तार करेगा।
printf '%s ' ={1..20}
=1 =2 =3 =4 =5 =6 =7 =8 =9 =10 =11 =12 =13 =14 =15 =16 =17 =18 =19 =20
और साथ printf '%.1s'जो वास्तव में मतलब है printf '%WIDE.LENGTH', हम केवल एक प्रिंट कर रहे हैं लंबाई डिफ़ॉल्ट के साथ ऊपर से उन लोगों में से 1 चौड़ा । तो परिणाम होगा= केवल 20 बार दोहराया जाएगा।
अब printf '%.20s:\n'हम केवल 20 की लंबाई की छपाई कर रहे हैं $strऔर यदि $str<20 की लंबाई है , तो शेष =रिक्त स्थान के बजाय भरने के लिए ले जाएगा ।