বাশকে কীভাবে যুক্তিটি alচ্ছিক হিসাবে তৈরি করবেন?


13

9 টি যুক্তি সহ নীচে ফাংশন:

SUM() { 
    echo "The sum is $(($1+$2+$3+$4+$5+$6+$7+$8+$9))"
}

আমি পরেরগুলিতে দ্বিতীয় আর্গুমেন্টটি তৈরি করতে চাই (3.9) একটি alচ্ছিক আর্গুমেন্ট হয়ে উঠতে

আমি যখন 2 টি যুক্তি দিয়ে ফাংশনটি কল করি তখন আমার ত্রুটি হয়:

SUM 3 8
bash: 3+8+++++++: syntax error: operand expected (error token is "+")

নোট বোল্ড : প্রথম আর্গুমেন্ট এবং দ্বিতীয় যুক্তি জোর যুক্তি এবং ফাংশনের জন্য alচ্ছিক নয়। আমি কেবল দ্বিতীয়টিতে আর্গুমেন্ট চাই alচ্ছিক এবং যখন আমি ফাংশনটি 2 টিরও কম কম কল করি তবে অবশ্যই কোনও ফল দিতে হবে না।

উত্তর:


22

আপনি যদি ফাঁক দিয়ে আর্গুমেন্টগুলি পাস না করেন:

sum() {  
[[ -n $2 ]] && echo $(( $(tr ' ' '+' <<<"$@") ))
}

প্রভাব:

$ sum 1 2 3
6

ব্যাখ্যা:

  1. <<<"some string"শুধুমাত্র "some string"ইনপুট হিসাবে ফিড । এটিকে শর্টহ্যান্ড হিসাবে বিবেচনা করুন echo "some string" |। একে হিয়ার স্ট্রিং বলা হয় ।
  2. "$@"সমস্ত অবস্থানগত পরামিতিগুলিতে স্পেস দ্বারা পৃথক করে প্রসারিত হয়। এটি সমান "$1 $2 ..."
  3. সুতরাং, tr ' ' '+' <<<"$@"আউটপুটগুলি "$1+$2+$3...", যা বাইরের দ্বারা মূল্যায়ন করা হয় $(( ))
  4. [[ -n $2 ]]দ্বিতীয় প্যারামিটারটি খালি না থাকলে পরীক্ষা করে। আপনি প্রতিস্থাপন করতে পারে [[ -n $2 ]] &&সঙ্গে [[ -z $2 ]] ||

অন্য উপায়:

sum() {
[[ -n $2 ]] && (IFS=+; echo $(( $* )))
}

ব্যাখ্যা:

  1. $*ঠিক যেমন $@, প্যারামিটারগুলি স্পেস দ্বারা পৃথক করা হয় না, তবে অভ্যন্তরীণ ক্ষেত্র পৃথককারী ( IFS) এর প্রথম অক্ষর দ্বারা । এর সাথে IFS=+এটি "$ 1 + $ 2 + ..." এ প্রসারিত হয়। দেখুন $ * এবং $ @ এর মধ্যে পার্থক্য কী?
  2. আমরা IFSএকটি সাব-শেল সেট করেছি (পার্শ্ববর্তী বন্ধনীগুলি নোট করুন) যাতে মূল শেলটি প্রভাবিত না হয়। IFSডিফল্টরূপে: \t\n(স্থান, ট্যাব, নিউলাইন)। এটি localভেরিয়েবলগুলি ব্যবহারের বিকল্প ।

এখন আপনার প্রশ্নের উত্তর দিতে:

যে কোনও ভেরিয়েবল বা প্যারামিটারের জন্য আপনি একটি ডিফল্ট মান ব্যবহার করতে পারেন । উভয় ক্ষেত্রেই:

SUM() { 
 echo "The sum is $(($1+$2+${3:-0}+${4:-0}+${5:-0}+${6:-0}+${7:-0}+${8:-0}+${9:-0}))" || false
}

বা:

SUM() { 
 echo "The sum is $(($1+$2+${3:=0}+${4:=0}+${5:=0}+${6:=0}+${7:=0}+${8:=0}+${9:=0}))" || false
}

6
নিফটি! আমি জানি মন্তব্যগুলি কৃতজ্ঞ প্রশংসা এবং ধন্যবাদ জন্য নয়, তবে এই সমাধানটি কেবল ... দুষ্ট! :-)
zwets

17

কটাক্ষপাত আছে shiftঅপারেটর। এটি আর্গুমেন্ট 2 এবং এর আগে অবস্থান 1 এবং পরবর্তী দিকে স্থানান্তর করবে, আর্গুমেন্ট 1 ত্যাগ করবে।

sum () {
    local total=0;
    while [ $# -gt 0 ]; do
        total=$(($total + $1))
        shift
    done
    echo $total
}

4

আপনি একটি পুনরাবৃত্ত সংজ্ঞা ব্যবহার করতে পারেন যা যখন sumআর্গুমেন্ট ছাড়াই ডাকা হয় তখন শেষ হয় ates আমরা testযুক্তি ছাড়াই মূল্যায়ন যে সত্য ব্যবহার false

sum () {
    test $1 && echo $(( $1 + $(shift; sum $@) )) || echo 0
}

3

এটা চেষ্টা কর:

SUM () {
 [ $# -lt "2" ] && return 1
 for par in $@; do
   local sum=`expr $sum + $par`
 done
 echo $sum
 return 0
}

SUM 3 4 5
SUM 3 4 5 1 1 1 1 2 3 4 5

এটি 12 এবং 30 আউটপুট দেবে।

$@পরামিতি বোঝায়, $#3 বা 11 ক্ষেত্রে এই ক্ষেত্রে প্যারামিটারের সংখ্যা দেয়।

লিনাক্স রেডহাট 4 এ পরীক্ষিত


2

আপনি কেবল একটি সামান্য লুপ ব্যবহার করতে পারেন:

sum(){
    t=0;
    for i in "$@"; do t=$((t + i )); done
    echo $t;
}

ব্যক্তিগতভাবে যদিও, আমি কেবল ব্যবহার করব perlবা awkপরিবর্তে:

sum(){
 echo "$@" | perl -lane '$s+=$_ for @F; print $s'
}

অথবা

sum(){
 echo "$@" | awk '{for(i=1; i<=NF; i++){k+=$i} print k}'
}

2

0 1 থেকে $ 9 এর জন্য ডিফল্ট মান হিসাবে 0 ব্যবহার করুন:

SUM() { 
    echo "The sum is $((${1:-0}+${2:-0}+${3:-0}+${4:-0}+${5:-0}+${6:-0}+${7:-0}+${8:-0}+${9:-0}))"
}

থেকে man bash:

${parameter:-word}
    Use Default Values. If parameter is unset or null, the expansion
    of word is substituted. Otherwise, the value of parameter is
    substituted.

উদাহরণ:

$ SUM

যোগফল 0

$ SUM 1 2 

যোগফল 3

$ SUM 1 1 1 1 1 1 1 1 1 

যোগফল 9


খালি সাথে একই আউটপুট:

SUM() {
  echo -e ${@/%/\\n} | awk '{s+=$1} END {print "The sum is " s}'
}

1

এটি আমার নিজস্ব সমাধানও আমি চেষ্টা করে দেখেছি:

SUM() { 
    echo "The sum is $(($1+$2+$[$3]+$[$4]+$[$5]+$[$6]+$[$7]+$[$8]+$[$9]))"
 }

$ SUM 4 6 5
The sum is 15

তবে @ মুড়ুর উত্তর ভাল।


+1: খালি প্যারামিটারগুলি শূন্যের মূল্যায়ন করতে দুটি গাণিতিক বিস্তারের আকর্ষণীয় ব্যবহার ।
মুরু

1
@ মুরু ধন্যবাদ, তবে এই ক্ষেত্রে আমার উত্তরটি আমরা 9 ​​টিরও বেশি যুক্তি ব্যবহার করি না এবং 9 টিরও বেশি পাস করার জন্য আমাদের একদল আর্গুমেন্ট ব্যবহার করতে হবে যা আপনার উত্তরটির জন্য সঠিক for
нιηসেস
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.