बैश गुणा और जोड़


18
for k in {0..49};
do
a=$(($((2*$k))+1));
echo $a;
done

नमस्ते, मुझे तीसरी पंक्ति के लिए एक सरलीकृत अभिव्यक्ति की आवश्यकता है, शायद एक जो कमांड प्रतिस्थापन का उपयोग नहीं करता है।


@ थियोफ्रेस्टस: जैसा कि सुझाव दिया गया है कि यह ठीक काम करता है लेकिन क्या होगा अगर मैं (()) के बजाय एक्सपायर का उपयोग करना चाहता हूं।
AVS

यह है bashऔर नहीं C, इसलिए सभी को हटा दें ;- जब तक कि आप इसे एक विलक्षण पंक्ति में न लिखें।
ott--


declare -i a; for k in {0..49}; do a=2*$k+1; echo $a; done
सायरस

1
एक तरफ: $(( ... ))अंकगणितीय विस्तार कमांड प्रतिस्थापन नहीं है।
dave_thompson_085

जवाबों:


28

अंकगणितीय विस्तार का उपयोग करना:

for (( k = 0; k < 50; ++k )); do
  a=$(( 2*k + 1 ))
  echo "$a"
done

पुरातन exprउपयोगिता का उपयोग :

for (( k = 0; k < 50; ++k )); do
  a=$( expr 2 '*' "$k" + 1 )
  echo "$a"
done

उपयोग करना bc -l( -lवास्तव में इस मामले में आवश्यक नहीं है क्योंकि कोई गणित कार्यों का उपयोग नहीं किया जाता है):

for (( k = 0; k < 50; ++k )); do
  a=$( bc -l <<<"2*$k + 1" )
  echo "$a"
done

bc -lसह-प्रक्रिया के रूप में उपयोग करना (यह पृष्ठभूमि में संगणना सेवा की तरह कार्य करता है):

coproc bc -l

for (( k = 0; k < 50; ++k )); do
  printf "2*%d + 1\n" "$k" >&${COPROC[1]}
  read -u "${COPROC[0]}" a
  echo "$a"
done

kill "$COPROC_PID"

यह आखिरी दिखता है (यकीनन) क्लीनर में ksh93:

bc -l |&
bc_pid="$!"

for (( k = 0; k < 50; ++k )); do
  print -p "2*$k + 1"
  read -p a
  print "$a"
done

kill "$bc_pid"

¹ इससे मेरे लिए एक बार एक समस्या हल हो गई, जहां मुझे एक बड़ी मात्रा में इनपुट को लूप में संसाधित करने की आवश्यकता थी। प्रसंस्करण के लिए कुछ फ्लोटिंग पॉइंट कंप्यूटेशन की आवश्यकता होती है, लेकिन स्पॉनिंगbc लूप में कुछ बार करने से यह काफी धीमा साबित होता है। हां, मैं इसे कई अन्य तरीकों से हल कर सकता था, लेकिन मैं ऊब गया था ...



5

आप letगणना को मजबूर करने के लिए कमांड का उपयोग कर सकते हैं ।

let a="2*k+1"

ध्यान दें कि हमें $kइस संरचना की आवश्यकता नहीं है ; एक साधारण kकाम करेगा।


4
यदि a=2whateverk+1वर्तमान निर्देशिका में कोई फ़ाइल है, तो वह विफल हो जाती है । इससे भी बदतर, अगर वहाँ एक फ़ाइल कहा जाता है a=2+b[$(reboot)]k+1, जो rebootकमांड को बुलाता है । यहां सबसे अच्छा उपयोग करना ((...))है ( ((a = 2 * k + 1))), या पोसिक्स सिंटैक्स:a=$((2 * k + 1))
स्टीफन चेज़लस

हम इसे उद्धृत कर सकते हैं; let a="2*k+1"उस को हल करने के लिए।
स्टीफन हैरिस

2

संभवतः आपके लिए आवश्यक अंकगणितीय विस्तार यह है:

a=$(( 1+2*k ))

वास्तव में, आपको एक चर का उपयोग करने की आवश्यकता नहीं है:

for k in {0..49}; do
    echo "$(( 1 + 2*k ))"
done

या गिनती चर एक for ((…))पाश में ले जाया जा सकता है :

for (( k=0;k<50;k++ )); do
    a=$(( 1+2*k ))
    printf '%s\n' "$a"
done

पाश के लिए

और, उस स्थिति में, लूप के लिए अंकगणितीय विस्तार को भी अंदर ले जाया जा सकता है:

for (( k=0 ; a=1+2*k , k<50 ;  k++)); do
    printf '%s\n' "$a"
done

या, किसी सरणी में सभी मान प्राप्त करने के लिए:

for (( k=0 ; a[k]=1+2*k , k<49 ;  k++ )); do :; done
printf '%s\n' "${a[@]}"

कोई सूत्र नहीं

लेकिन शायद किसी भी अंकगणित के विस्तार से बचने का सबसे छोटा तरीका दो बार एक चर बढ़ाना है:

for (( k=0,a=1 ; k<50 ;  k++,a++,a++ )); do
    printf '%s\n' "$a"
done

या, और भी सरल, बस seq का उपयोग करें:

seq 1 2 100
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.