একটি সংখ্যায় হাজার হাজার বিভাজক যুক্ত করুন


37

অজগরে

 re.sub(r"(?<=.)(?=(?:...)+$)", ",", stroke ) 

একটি সংখ্যা ট্রিপল্ট দ্বারা বিভক্ত করতে যেমন:

 echo 123456789 | python -c 'import sys;import re; print re.sub(r"(?<=.)(?=(?:...)+$)", ",",  sys.stdin.read());'
 123,456,789

বাশ / অজকের সাথে একই কীভাবে করবেন?

উত্তর:


29

সাথে sed:

$ echo "123456789" | sed 's/\([[:digit:]]\{3\}\)\([[:digit:]]\{3\}\)\([[:digit:]]\{3\}\)/\1,\2,\3/g'
123,456,789

(দ্রষ্টব্য যে এটি কেবল 9 ডিজিটের জন্য কাজ করে!)

বা এটি সহ sed:

$ echo "123456789" | sed ':a;s/\B[0-9]\{3\}\>/,&/;ta'
123,456,789

সাথে printf:

$ LC_NUMERIC=en_US printf "%'.f\n" 123456789
123,456,789

আমিও বুদ্ধি দিয়ে চেষ্টা করছি তবে এটি শেষের দিকে কমা যুক্ত করেছেecho 123456789 | awk '$0=gensub(/(...)/,"\\1,","g")'
রাহুল পাতিল

এখন আমি পেয়েছি তবে এটি জটিল বলে মনে হচ্ছেecho 123456789 | awk '$0=gensub(/(...)/,"\\1,","g"){sub(",$",""); print}'
রাহুল পাতিল

1
যে প্রথম sedযদি সংখ্যা ঠিক 9 টি সংখ্যা মাত্র কাজ করে। printfZsh উপর কাজ করে না। সুতরাং দ্বিতীয় sedউত্তর সম্ভবত সেরা।
প্যাট্রিক

1
@ রাহুলপাতিল এটি কেবলমাত্র অঙ্কের সংখ্যা 3 এর গুণক হলে সঠিকভাবে কাজ করে "12345678" দিয়ে চেষ্টা করুন এবং আপনি কী বোঝাতে চাইছেন তা আপনি দেখতে পাবেন।
প্যাট্রিক

1
আপনি echo 123456789 | awk '{printf ("%'\''d\n", $0)}'যা করতে পারেন (যা স্পষ্টতই লিনাক্সে সর্বদা কাজ করে না!?, তবে এআইএক্স এবং সোলারিসে ভাল কাজ করে)
জোহান

51

bashএর সি কার্যক্রমে printfআপনি যা করতে পারেন তা অনেক কিছুই সমর্থন printfকরে

type printf           # => printf is a shell builtin
printf "%'d" 123456   # => 123,456

printf কোর্টিল থেকে একই কাজ করবে

/usr/bin/printf "%'d" 1234567   # => 1,234,567

এটি এখন সমর্থিত zshখুব, আপডেট পোস্ট এখানে
don_crissti

1
আমি ৪.১.২ ব্যাশে আছি এবং এটি সমর্থন করে না ... :(
এমএসবি

@ এমএসবি এটি আপনার সিস্টেমের উপর নির্ভর করে বলে মনে হচ্ছে vsnprintf। একটি জিএনইউ / লিনাক্স সিস্টেমে, গ্লিবসি অন্তত 1995 সাল থেকে এটি সমর্থন করেছে বলে মনে হয়
মিকেল

2
নোট প্রিন্টফ আপনার বর্তমান লোকেলের জন্য কয়েক হাজার বিভাজক ব্যবহার করে , যা কমা, বিন্দু বা কিছুই হতে পারে না। আপনি export LC_NUMERIC="en_US"যদি কমাতে বাধ্য করতে চান তবে আপনি পারেন।
মেডমন্ডস

সমর্থিত লোকেলের সাথে তালিকা পান locale -a। আমাকে ব্যবহার করতে হয়েছিলen_US.utf8

7

আপনি numfmt ব্যবহার করতে পারেন:

$ numfmt --grouping 123456789
123,456,789

বা:

$ numfmt --g 123456789
123,456,789

নোটফ্যামটি কোনও পসিক্স ইউটিলিটি নয়, এটি জিএনইউ কোর্টিলগুলির অংশ til


1
"গ্রুপিং" টিপসের জন্য ধন্যবাদ। দ্বিতীয় উদাহরণে (--g), -d, --groupingডাবল হাইফেনেশনের দীর্ঘ বিকল্পের প্রয়োজন হওয়ার কারণে আপনি কি এমন কিছু লিখতে চান ?
শে

--gপরিবর্তে আমার জন্য ভাল কাজ করে --grouping, numfmt --g 1234567890এবং numfmt --grouping 1234567890একই জিনিস। এটি একটি খুব দরকারী সামান্য ইউটিলিটি।
ম্যাটসেট

4
cat <<'EOF' |
13407807929942597099574024998205846127479365820592393377723561443721764030073546976801874298166903427690031858186486050853753882811946569946433649006084096
EOF
perl -wpe '1 while s/(\d+)(\d\d\d)/$1,$2/;'

সৃষ্টি করে:

13,407,807,929,942,597,099,574,024,998,205,846,127,479,365,820,592,393,377,723,561,443,721,764,030,073,546,976,801,874,298,166,903,427,690,031,858,186,486,050,853,753,882,811,946,569,946,433,649,006,084,096

এটি অঙ্কের স্ট্রিংটি 2 টি গোষ্ঠীতে বিভক্ত করে ডান-হাতের গ্রুপকে 3 টি সংখ্যা দিয়ে, বাম-হাতের দলটি যা বাকী রয়েছে তার সাথে কমপক্ষে একটি অঙ্কে বিভক্ত করা যায়। তারপরে সবকিছু কমা দ্বারা পৃথক করে 2 টি গোষ্ঠী দ্বারা প্রতিস্থাপিত হবে। প্রতিস্থাপন ব্যর্থ হওয়া অবধি এটি অব্যাহত থাকে। "ডাব্লুপিই" বিকল্পগুলি ত্রুটি তালিকাভুক্ত করার জন্য, একটি লুপের ভিতরে একটি স্বয়ংক্রিয় প্রিন্টের সাহায্যে বিবৃতিটি আবদ্ধ করুন এবং পরবর্তী যুক্তিটি পার্ল "প্রোগ্রাম" হিসাবে গ্রহণ করুন (বিশদ বিবরণের জন্য কমান্ড পার্ল্ডোক পার্ল্রুন দেখুন)।

শুভকামনা ... চিয়ার্স, ড্রল


প্রতিক্রিয়ার জন্য বেনামে ধন্যবাদ। এমনকি একটি ডাউনভোটও কার্যকর হতে পারে তবে কেবল যদি ব্যাখ্যা করা হয় - দয়া করে আপনি যা দেখেছেন তা ভুল বলে মন্তব্য করুন। ধন্যবাদ ... চিয়ার্স
'15 1515 এ ড্রল

আমি মনে করি এখানে ডাউনটোটটি হ'ল কারণ আপনি আদেশটি কী করেন তা ব্যাখ্যা করেন নি। ওপি BASH/ AWKবিকল্পের জন্য জিজ্ঞাসা করেছিল যাতে সে PERLআগে ব্যবহার না করে । যে কোনও ক্ষেত্রে, কমান্ডটি কী করে তা বোঝানো ভাল - বিশেষত ওয়ান-লাইনারদের জন্য।
অ্যান্থনিকে

@ অ্যান্থোনিকে - সম্ভাব্য ব্যাখ্যার জন্য ধন্যবাদ এটি কীভাবে কাজ করে তা সংক্ষেপে ব্যাখ্যা করার জন্য আমি মন্তব্য যুক্ত করেছি। আমি মনে করি বিকল্প সমাধানগুলি প্রায়শই দরকারী, তবে সম্ভবত পার্ল ব্যবহার না করার বিষয়ে আপনার
বক্তব্যটি

আমি এই পৃষ্ঠায় sed এবং অজগর পরামর্শ চেষ্টা করেছিলাম। পার্ল স্ক্রিপ্টটি কেবলমাত্র একটি সম্পূর্ণ ফাইলের জন্য কাজ করেছিল। ফাইলটি পাঠ্য এবং নম্বর সহ ফাইল করা হয়েছিল।
চিহ্নিত করুন

3

কিছু awkবাস্তবায়ন সহ:

echo "123456789" | awk '{ printf("%'"'"'d\n",$1); }'  

123,456,789  

"%'"'"'d\n"হ'ল: "%(একক উদ্ধৃতি) (ডাবল উদ্ধৃতি) (একক উদ্ধৃতি) (ডাবল উদ্ধৃতি) (একক উদ্ধৃতি) d \ n"

এটি আপনার লোকেলের জন্য কনফিগার করা সহ হাজার বিভাজক ব্যবহার করবে (সাধারণত ,ইংরেজি স্থানীয়, ফরাসি ভাষা, .স্প্যানিশ / জার্মান ভাষায় ...)। দ্বারা ফেরত হিসাবে একইlocale thousands_sep


2

আমার কাছে একটি সাধারণ ব্যবহারের ক্ষেত্রে হ'ল একটি কমান্ড পাইপলাইনের আউটপুট পরিবর্তন করা যাতে দশমিক সংখ্যা হাজার বিভাজক দ্বারা মুদ্রিত হয়। কোনও ফাংশন বা স্ক্রিপ্ট লেখার পরিবর্তে, আমি কোনও কৌশল ব্যবহার করতে পছন্দ করি যা আমি ইউনিক্স পাইপলাইন থেকে যে কোনও আউটপুটের জন্য ফ্লাইতে কাস্টমাইজ করতে পারি ।

আমি এটি printfঅর্জন করার জন্য সবচেয়ে নমনীয় এবং স্মরণীয় উপায় (আউক দ্বারা সরবরাহিত) পেয়েছি । ঊর্ধকমা / একক উদ্ধৃতি অক্ষর দ্বারা নির্দিষ্ট করা POSIX হিসেবে পরিবর্তক বিন্যাস দশমিক নম্বরে এবং সুবিধা হল যে এটা লোকেল সচেতন তাই এটা কমা অক্ষর ব্যবহার করে অবধি সীমিত নয় হয়েছে।

ইউনিক্স শেল থেকে আওক কমান্ড চালানোর সময়, একক উদ্ধৃতি দ্বারা ডিলিমিট স্ট্রিংয়ের ভিতরে সিং-কোট অক্ষর প্রবেশ করা অসুবিধা হতে পারে (অবস্থানগত ভেরিয়েবলগুলির শেল প্রসার এড়াতে, যেমন, $1)। এই ক্ষেত্রে, আমি একক-উদ্ধৃতি চরিত্রটি প্রবেশ করার সর্বাধিক পঠনযোগ্য এবং নির্ভরযোগ্য উপায়টি হ'ল এটি একটি অষ্টাল পালানোর ক্রম হিসাবে প্রবেশ করা (শুরু দিয়ে \0)।

উদাহরণ:

printf "first 1000\nsecond 10000000\n" |
  awk '{printf "%9s: %11\047d\n", $1, $2}'
  first:       1,000
 second:  10,000,000

কোন ডিরেক্টরিগুলি সর্বাধিক ডিস্ক স্থান ব্যবহার করে তা দেখায় এমন পাইপলাইনের সিমুলেটেড আউটপুট:

printf "7654321 /home/export\n110384 /home/incoming\n" |
  awk '{printf "%22s: %9\047d\n", $2, $1}'
  /home/export: 7,654,321
/home/incoming:   110,384

অন্যান্য সমাধানগুলিতে কীভাবে আস্তে আস্তে একটি একক উদ্ধৃতি থেকে বাঁচতে হয় তার তালিকাভুক্ত করা হয়েছে ।

দ্রষ্টব্য: একক উদ্ধৃতি প্রিন্টের বিরুদ্ধে যেমন সতর্ক করা হয়েছিল , হেক্সাডেসিমাল এস্কেপ সিকোয়েন্সগুলি এড়াতে বাঞ্ছনীয় কারণ তারা বিভিন্ন সিস্টেমে নির্ভরযোগ্যভাবে কাজ করে না।


1
এখানে তালিকাভুক্ত সমস্ত অবাস্তব-ভিত্তিক উত্তরগুলির মধ্যে, এটি অবশ্যই সবচেয়ে কৃপণ (আইএমএইচও)। অন্য সমাধানগুলির মতো অন্যান্য উদ্ধৃতিগুলির সাথে একটি উদ্ধৃতিতে হ্যাক করার প্রয়োজন নেই।
TSJNachos117

ধন্যবাদ @ টিএসজেএনচোস ১১7 সবচেয়ে কঠিন অংশটি মনে করছে যে অ্যাডোস্ট্রোফ চরিত্রটির জন্য অষ্টাল এনকোডিং \047
অ্যান্টনি জি - মনিকার

2

awkএবং অন্যান্য উত্তরে বর্ণিত হিসাবে bashভিত্তিতে ভাল অন্তর্নিহিত সমাধান রয়েছে printf। তবে প্রথম sed,।

কারণ sed, আমাদের এটি "ম্যানুয়ালি" করা দরকার। সাধারণ নিয়মটি হ'ল যদি আপনার কাছে টানা চারটি অঙ্ক থাকে, তার পরে একটি অ-অঙ্ক (বা লাইন-এর শেষে) থাকে তবে প্রথম এবং দ্বিতীয় অঙ্কের মধ্যে একটি কমা beোকানো উচিত।

উদাহরণ স্বরূপ,

echo 12345678 | sed -re 's/([0-9])([0-9]{3})($|[^0-9])/\1,\2\3/'

মুদ্রণ করবে

12345,678

পর্যাপ্ত কমা যোগ করার জন্য আমাদের অবশ্যই প্রক্রিয়াটি পুনরাবৃত্তি করতে হবে।

sed -re ' :restart ; s/([0-9])([0-9]{3})($|[^0-9])/\1,\2\3/ ; t restart '

ইন sed, tকমান্ডটি এমন একটি লেবেল নির্দিষ্ট করে যা শেষ s///কমান্ডটি সফল হলে লাফানো হবে । অতএব আমি একটি লেবেলটি সংজ্ঞায়িত করি :restartযাতে এটি পিছনে আসে।

এখানে একটি বাশ ডেমো রয়েছে ( আইডিয়োনে ) যা সংখ্যার সংখ্যার সাথে কাজ করে:

function thousands {
    sed -re ' :restart ; s/([0-9])([0-9]{3})($|[^0-9])/\1,\2\3/ ; t restart '
}                                                 
echo 12 | thousands
echo 1234 | thousands
echo 123456 | thousands
echo 1234567 | thousands
echo 123456789 | thousands
echo 1234567890 | thousands


1

আপনি যদি বিআইজি নম্বরগুলি দেখেন তবে আমি উপরের সমাধানগুলি কাজ করতে অক্ষম ছিলাম। উদাহরণস্বরূপ, আসুন সত্যিকারের একটি বড় সংখ্যা পান:

$ echo 2^512 |bc -l|tr -d -c [0-9] 13407807929942597099574024998205846127479365820592393377723561443721764030073546976801874298166903427690031858186486050853753882811946569946433649006084096

দ্রষ্টব্য, আমাকে trবিসি থেকে ব্যাকস্ল্যাশ নিউলাইন আউটপুট অপসারণ করতে হবে। এই সংখ্যাটি অজানা অবস্থায় একটি ফ্লোট বা স্থির বিট সংখ্যা হিসাবে বিবেচনা করার জন্য খুব বড় এবং আমি সেডে সমস্ত সংখ্যার জন্য অ্যাকাউন্ট তৈরি করতে যথেষ্ট বড় একটি রেজিপ্সপ তৈরি করতে চাই না। পরিবর্তে, আমি এটিকে বিপরীত করতে এবং তিন অঙ্কের গোষ্ঠীর মধ্যে কমা রাখতে পারি, তারপরে এটিকে বিপরীতমুখী করুন:

echo 2^512 |bc -l|tr -d -c [0-9] |rev |sed -e 's/\([0-9][0-9][0-9]\)/\1,/g' |rev 13,407,807,929,942,597,099,574,024,998,205,846,127,479,365,820,592,393,377,723,561,443,721,764,030,073,546,976,801,874,298,166,903,427,690,031,858,186,486,050,853,753,882,811,946,569,946,433,649,006,084,096


2
ভাল উত্তর. যাইহোক, আমি Awk এর সাথে বৃহত সংখ্যক ব্যবহার করে কোন সমস্যায় পড়িনি। আমি রেড হ্যাট এবং ডেবিয়ান-ভিত্তিক বিতরণগুলির কয়েকটিতে আপনার উদাহরণটি চেষ্টা করেছি তবে সব ক্ষেত্রেই, অওকের বড় সংখ্যায় কোনও সমস্যা ছিল না। আমি এটি সম্পর্কে আরও কিছু ভেবেছিলাম এবং এটি আমার কাছে ঘটেছিল যে আমি যে সমস্ত সিস্টেমে পরীক্ষা করেছি সেগুলি ৪-বিট (এমনকি একটি পুরানো ভিএম অসমর্থিত আরএইচএল 5 চালাচ্ছে)। পর্যন্ত আমি একটি পুরানো ভাঁজ-টপ একটি 32 বিট অপারেটিং সিস্টেম যে আমি আপনার সমস্যাটি প্রতিলিপি করতে সক্ষম হন চলমান পরীক্ষা করা ছিল: awk: run time error: improper conversion(number 1) in printf("%'d
অ্যান্টনি জি -

1
a="13407807929942597099574024998205846127479365820592393377723561443721764030073546976801874298166903427690031858186486050853753882811946569946433649006084096"

echo "$a" | rev | sed "s#[[:digit:]]\{3\}#&,#g" | rev

13,407,807,929,942,597,099,574,024,998,205,846,127,479,365,820,592,393,377,723,561,443,721,764,030,073,546,976,801,874,298,166,903,427,690,031,858,186,486,050,853,753,882,811,946,569,946,433,649,006,084,096

এটা একটা কৃত্রিম নেতৃস্থানীয় কমা যোগ যদি সংখ্যায় ডিজিটের সংখ্যা 3. এর গুণিতক হয়
Stéphane Chazelas

@ স্টাফেনচেজেলাস: আপনি সর্বশেষ রেভ কমান্ডের আউটপুট নিতে এবং এটিতে পাইপ করতে পারেন sed 's/^,//g'
TSJNachos117

0

আমিও অংশ চেয়েছিলেন পর দশমিক বিভাজক সঠিকভাবে পৃথক / ব্যবধানে, অতএব আমি এই sed-স্ক্রিপ্ট যা আঞ্চলিক ও ব্যক্তিগত পছন্দ সমন্বয় কিছু শেল ভেরিয়েবল ব্যবহার লিখেছিলেন। এটি একসাথে গোষ্ঠীযুক্ত সংখ্যার জন্য পৃথক কনভেনশনগুলিও আমলে নেয় :

#DECIMALSEP='.' # usa                                                                                                               
DECIMALSEP=','  # europe

#THOUSSEP=',' # usa
#THOUSSEP='.' # europe
#THOUSSEP='_' # underscore
#THOUSSEP=' ' # space
THOUSSEP=' '  # thinspace

# group before decimal separator
#GROUPBEFDS=4   # china
GROUPBEFDS=3    # europe and usa

# group after decimal separator
#GROUPAFTDS=5   # used by many publications 
GROUPAFTDS=3


function digitgrouping {
  sed -e '
    s%\([0-9'"$DECIMALSEP"']\+\)'"$THOUSSEP"'%\1__HIDETHOUSSEP__%g
    :restartA ; s%\([0-9]\)\([0-9]\{'"$GROUPBEFDS"'\}\)\(['"$DECIMALSEP$THOUSSEP"']\)%\1'"$THOUSSEP"'\2\3% ; t restartA
    :restartB ; s%\('"$DECIMALSEP"'\([0-9]\{'"$GROUPAFTDS"'\}\'"$THOUSSEP"'\)*\)\([0-9]\{'"$GROUPAFTDS"'\}\)\([0-9]\)%\1\3'"$THOUSSEP"'\4% ; t restartB
    :restartC ; s%\([^'"$DECIMALSEP"'][0-9]\+\)\([0-9]\{'"$GROUPBEFDS"'\}\)\($\|[^0-9]\)%\1'"$THOUSSEP"'\2\3% ; t restartC
    s%__HIDETHOUSSEP__%\'"$THOUSSEP"'%g'
}

0

একটি bash/ awk(অনুরোধ হিসাবে) সমাধান যা সংখ্যার দৈর্ঘ্য ,নির্বিশেষে এবং লোকেলের thousands_sepসেটিং নির্বিশেষে ব্যবহার করে এবং যেখানেই সংখ্যাগুলি ইনপুটটিতে রয়েছে এবং সেখানে সহস্র বিভাজক যুক্ত করা এড়িয়ে চলে 1.12345:

echo not number 123456789012345678901234567890 1234.56789 |
  awk '{while (match($0, /(^|[^.0123456789])[0123456789]{4,}/))
        $0 = substr($0, 1, RSTART+RLENGTH-4) "," substr($0, RSTART+RLENGTH-3)
        print}'

দেয়:

not number 123,456,789,012,345,678,901,234,567,890 1,234.56789

এর awkমতো বাস্তবায়নগুলি mawkঅন্তর্বর্তী রেজেক্স অপারেটরগুলিকে সমর্থন করে না, রিজেক্সেপকে এতে পরিবর্তন করুন/(^|[^.0123456789])[0123456789][0123456789][0123456789][0123456789]+/

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.