দুটি দশমিক পয়েন্টে ভাসমান সীমাবদ্ধ


1689

আমি 13.95 এa বৃত্তাকার হতে চাই ।

>>> a
13.949999999999999
>>> round(a, 2)
13.949999999999999

roundফাংশন উপায় আমি আশা কাজ করে না।



6
হুম ... আপনি কি মুদ্রা উপস্থাপন করার চেষ্টা করছেন? যদি তা হয় তবে আপনার ডলারের বিনিময়ে ফ্লোট ব্যবহার করা উচিত নয়। আপনি সম্ভবত পেনিগুলির জন্য ফ্লোটগুলি ব্যবহার করতে পারেন, বা আপনি যে মুদ্রার ক্ষুদ্রতম সাধারণ ইউনিটকে মডেল করার চেষ্টা করছেন তা যা ঘটেছিল তা হ'ল, তবে হুগাগুAHাহ তার উত্তরে বলেছিলেন, তবে সবচেয়ে ভাল অনুশীলন দশমিক প্রতিনিধিত্ব ব্যবহার করা।
সিঙ্গেলাইজেশন ইলিমিনেশন

63
ফ্লোটে মুদ্রা উপস্থাপন না করা গুরুত্বপূর্ণ। ফ্লোটগুলি সুনির্দিষ্ট নয়। কিন্তু পেনি বা শতকরা পরিমাণ পূর্ণসংখ্যা। সুতরাং পূর্ণসংখ্যাগুলি মুদ্রা উপস্থাপনের সঠিক উপায়।
দাউদ তাগাওহী-নেজাদ

2
@ দাউদটাঘাবি-নেজাদ বা আরও কিছু কথা ... দশমিক প্রকার
বেসিক

17
আমি সম্ভবত এখানে খুব দেরিতে আসছি, তবে আমি জিজ্ঞাসা করতে চেয়েছিলাম, পাইথনের বিকাশকারীরা কি এই সমস্যাটি সমাধান করেছেন? কারণ যখন আমি রাউন্ডটি করি (13.949999999999999, 2), আমি কেবল 13.95 পেয়ে যাই। আমি এটি পাইথন ২.7..6 এও 3.4 তে চেষ্টা করেছি। এটা কাজ করে। ২. Not এমনকি ২০০৯-এ ছিল কিনা তা নিশ্চিত নয় Maybe সম্ভবত এটি পাইথন 2.5 এর জিনিস?
খারাপ_কিপয়েন্ট

উত্তর:


1685

আপনি ভাসমান পয়েন্ট সংখ্যাগুলি সহ পুরানো সমস্যাটির মধ্যে চলে যাচ্ছেন যে সমস্ত সংখ্যা হুবহু উপস্থাপন করা যায় না। কমান্ড লাইনটি আপনাকে স্মৃতি থেকে সম্পূর্ণ ভাসমান পয়েন্ট ফর্মটি দেখায়।

ভাসমান পয়েন্ট উপস্থাপনা সহ, আপনার বৃত্তাকার সংস্করণ একই সংখ্যা number যেহেতু কম্পিউটারগুলি বাইনারি হয় তাই তারা ভাসমান পয়েন্ট সংখ্যাগুলি একটি পূর্ণসংখ্যার হিসাবে সংরক্ষণ করে এবং তারপরে এটি দুটি দিয়ে শক্তিকে বিভক্ত করে তাই ১৩.৯৫ একই ধরণের উপায়ে 125650429603636838 / (২ ** 53) তে উপস্থাপিত হবে।

ডাবল স্পষ্টতা সংখ্যায় যথাযথতার 53 বিট (16 ডিজিট) থাকে এবং নিয়মিত ফ্লোটগুলিতে 24 বিট (8 ডিজিট) যথার্থ থাকে। পাইথন মধ্যে ফ্লোটিং পয়েন্ট টাইপ ডবল স্পষ্টতা ব্যবহার মান সংরক্ষণ করতে।

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

>>> 125650429603636838/(2**53)
13.949999999999999

>>> 234042163/(2**24)
13.949999988079071

>>> a = 13.946
>>> print(a)
13.946
>>> print("%.2f" % a)
13.95
>>> round(a,2)
13.949999999999999
>>> print("%.2f" % round(a, 2))
13.95
>>> print("{:.2f}".format(a))
13.95
>>> print("{:.2f}".format(round(a, 2)))
13.95
>>> print("{:.15f}".format(round(a, 2)))
13.949999999999999

যদি আপনি কেবলমাত্র দুটি দশমিক জায়গার পরে থাকেন (উদাহরণস্বরূপ একটি মুদ্রার মান প্রদর্শন করতে), তবে আপনার কাছে আরও কয়েকটি ভাল পছন্দ রয়েছে:

  1. ডলার নয়, সেন্টে পূর্ণসংখ্যা এবং স্টোর মানগুলি ব্যবহার করুন এবং তারপরে ডলারে রূপান্তর করতে 100 দ্বারা ভাগ করুন।
  2. অথবা দশমিকের মতো একটি নির্দিষ্ট পয়েন্ট নম্বর ব্যবহার করুন ।

27
@ ক্রিশ্চিয়ান সঞ্চিত মান এবং কীভাবে আপনি সেই মানটি প্রদর্শন করেন তার মধ্যে একটি মৌলিক পার্থক্য রয়েছে । আউটপুট ফর্ম্যাট করা আপনাকে প্রয়োজনমতো প্যাডিং যোগ করার পাশাপাশি কমা বিভাজক ইত্যাদি যোগ করার অনুমতি দেবে
বেসিক

22
মূল্য উল্লেখ করে "%.2f" % round(a,2)তোমার মত না শুধুমাত্র printf মধ্যে, কিন্তু এই ধরনের জিনিস মধ্যে লাগাতে পারেনstr()
andilabs

20
কেন লোকেরা সর্বদা ভাসমান-পয়েন্ট গোলকে মুদ্রা ধরে রাখে? কখনও কখনও আপনি কেবল কম নির্ভুলতার সাথে কাজ করতে চান।
worc

9
@ অ্যাডটেক: আপনার বুঝতে হবে যে বাইনারি মান (টাইপের float) হ'ল দশমিক সংখ্যার নিকটতম উপলব্ধ সন্নিকরণ (যে আপনি মানুষ হিসাবে পরিচিত as 0.245 এর মতো কোনও (চূড়ান্তভাবে উপস্থাপনযোগ্য) বাইনারি মান নেই। এটি কেবল অস্তিত্বহীন, এবং গাণিতিকভাবে বিদ্যমান থাকতে পারে না । বাইনারি মান যা 0.245 এর নিকটতম, এটি 0.245 এর থেকে সামান্য কম , তাই স্বাভাবিকভাবেই এটি গোল হয়ে যায়। একইভাবে, বাইনারিতে 0.225 এর মতো কোনও জিনিস নেই তবে বাইনারি মান যা 0.225 এর নিকটবর্তী হয় এটি 0.225 এর চেয়ে সামান্য বেশি , তাই স্বাভাবিকভাবেই এটি চারদিকে আসে।
জন ওয়াই

12
@ অ্যাডটেক: আপনি আক্ষরিক ব্যাখ্যা চেয়েছিলেন? সর্বাধিক সরল সমাধান হ'ল সত্যই ব্যবহার করা Decimalএবং এটি ছিল এই উত্তরের একটি সমাধান। অন্যটি হ'ল আপনার পরিমাণকে পূর্ণসংখ্যায় রূপান্তর করা এবং পূর্ণসংখ্যার গাণিতিক ব্যবহার করা। এই উভয় পদ্ধতিরই অন্যান্য উত্তর এবং মন্তব্যে হাজির।
জন ওয়াই

586

নতুন ফর্ম্যাট স্পেসিফিকেশন রয়েছে, স্ট্রিং ফর্ম্যাট স্পেসিফিকেশন মিনি-ল্যাঙ্গুয়েজ :

আপনি একই হিসাবে করতে পারেন:

"{:.2f}".format(13.949999999999999)

নোট 1: উপরেরটি একটি স্ট্রিং প্রদান করে। ভাসমান হিসাবে পেতে, কেবল এগুলি দিয়ে মুড়িয়ে দিন float(...):

float("{:.2f}".format(13.949999999999999))

দ্রষ্টব্য 2: দিয়ে মোড়ানো float()কোনও পরিবর্তন করে না:

>>> x = 13.949999999999999999
>>> x
13.95
>>> g = float("{:.2f}".format(x))
>>> g
13.95
>>> x == g
True
>>> h = round(x, 2)
>>> h
13.95
>>> x == h
True

17
কমা যুক্ত করতে পাশাপাশি '{0:,.2f}'.format(1333.949999999)প্রিন্ট করতে পারেন '1,333.95'
স্টিফেন ব্লাম

@ অনুরওয়াল্ডারম: হ্যাঁ, তবে আপনি এটি দিয়ে মুড়িয়ে দিতে পারেন float(); float("{0:.2f}".format(13.9499999))
জোসেফ হারুশ

5
@ জোসেফ হারুশ আপনি এটি ভাসা () দিয়ে মুড়িয়ে রাখতে পারেন তবে আপনি কিছু পাননি। এখন আপনার আবার একই ভাসাটি রয়েছে all 13.9499999999999 এবং 13.95 একই ভাসা।
নেড ব্যাচেল্ডার

4
@ নেডব্যাচেল্ডার: আমি সম্মত হই যে তারা সমান, তবে এটি
ভাসমানটিকে

8
যাইহোক, পাইথন ৩.6 থেকে আমরা এফ-স্ট্রিংগুলি ব্যবহার করতে পারি:f"Result is {result:.2f}"
আন্দ্রে সেমাকিন

289

বিল্ট-ইন round()পাইথন ২. 2. বা তার ঠিক পরে কাজ করে।

উদাহরণ:

>>> round(14.22222223, 2)
14.22

ডকুমেন্টেশন পরীক্ষা করে দেখুন ।


1
সুতরাং আমি বুঝতে পারি যে এটি পাইথন ২. 2. ব্যর্থ হয়েছে? কেন এই জাতীয় মৌলিক ক্রিয়াকলাপটি ভি 2.7 থেকে ভ 3 এর বিভিন্ন ফল পাবে?
মাইকম

কিন্তু round(2.16, 1)দিতে 2.2কেন পাইথন শুধু একটি প্রস্তাব truncatefunc
jiamo

উদাহরণস্বরূপ, আপনি যদি ২.6 to৫ থেকে দুটি দশমিক স্থানে মানটি চেষ্টা করে থাকেন তবে আপনি এই >>> round(2.675, 2) 2.67 ডকসটি
বিপদে

4
পাইথন 3 ডকুমেন্টেশন পৃষ্ঠা থেকে:Note The behavior of round() for floats can be surprising: for example, round(2.675, 2) gives 2.67 instead of the expected 2.68. This is not a bug: it’s a result of the fact that most decimal fractions can’t be represented exactly as a float.
রিচার্ড ডেলি

নোট করুন যে আপনি যদি এই পদ্ধতিটি ১.০০০০০০ প্রিন্ট করার জন্য ব্যবহার করার চেষ্টা করেন তবে এটি আপনি যে পরিমাণে দশমিক পয়েন্ট উল্লেখ করেছেন তা নির্বিশেষে এটি কেবল ১.০ মুদ্রণ করবে।
জোশ কোরিয়া

142

আমি অনুভব করি যে format()ফাংশনটি ব্যবহার করা সবচেয়ে সহজ পদ্ধতির ।

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

a = 13.949999999999999
format(a, '.2f')

13.95

এটি দুটি দশমিক পয়েন্টকে বৃত্তাকার স্ট্রিং হিসাবে একটি ফ্লোট সংখ্যা তৈরি করে।


97

ব্যবহার

print"{:.2f}".format(a)

পরিবর্তে

print"{0:.2f}".format(a)

কারণ একাধিক ভেরিয়েবল আউটপুট দেওয়ার চেষ্টা করার পরে উত্তরগুলি আউটপুট ত্রুটির দিকে পরিচালিত করতে পারে (মন্তব্য দেখুন)।


2
এটা অপদার্থ. প্রদত্ত দুটি বিবৃতি পাইথন ২.7 এ একইরকম আচরণ করে এবং কেবলমাত্র দ্বিতীয় বিবৃতি পাইথন ২.6 এ বৈধ is (পাইথন 3 বা পাইথনে কোনও বিবৃতি বৈধ নয় <2.6।) প্রথম রূপের ব্রেভিটি ছাড়া কোনও সুবিধা নেই।
মার্ক ডিকিনসন

1
মানে, "{0: .2f} {0: .2f}" মুদ্রণ করুন। ফর্ম্যাট (ক, খ) আউটপুটে ভুল হতে পারে - এটি 'a' মানকে দুবার আউটপুট দেবে। "{:। 2f} {: .2f}" প্রিন্ট করার সময়। ফর্ম্যাট (ক, খ) 'এ' এবং 'বি' মান আউটপুট করবে।
আলেক্সি আন্তোনেঙ্কো

2
পাইথন 3 এর জন্য আপনাকে কেবল বন্ধনী প্রিন্ট (...) যুক্ত করতে হবে। এবং তাদের মধ্যে আমি যা লিখেছি তা ঠিক।
আলেক্সি আন্তোনেনকো

"আমার অর্থ, মুদ্রণ করুন" {0: .2f} {0: .2f} "। ফর্ম্যাট (ক, খ) আউটপুটতে ভুল হতে পারে"। আহ। ঠিক আছে, এটি একটি সম্পূর্ণ বিবৃতি! আপনার উত্তর সম্পাদনা করা উচিত? (বর্তমান উত্তরের "ত্রুটি বাড়ানো" এর অর্থ কী, উদাহরণস্বরূপ? আপনি কি এমন একটি মামলার উদাহরণ দিতে পারেন যেখানে দ্বিতীয় বিবৃতি ব্যতিক্রম উত্থাপন করে তবে প্রথমটি দেয় না?)
মার্ক ডিকিনসন

3
আপনি মুদ্রণের পরে ("{0: .2f} {1: .2f}"। ফর্ম্যাট (ক, খ)) আপনার দুটি ভেরিয়েবল থাকলে
হোভো

95

বেশিরভাগ সংখ্যা ভাসমানগুলিতে হুবহু উপস্থাপন করা যায় না। আপনি যদি অঙ্কটি গোল করতে চান কারণ এটি আপনার গাণিতিক সূত্র বা অ্যালগরিদমের প্রয়োজন তাই আপনি রাউন্ডটি ব্যবহার করতে চান। আপনি যদি কেবল প্রদর্শনটিকে একটি নির্দিষ্ট নির্ভুলতার মধ্যে সীমাবদ্ধ করতে চান তবে রাউন্ডটি ব্যবহার করবেন না এবং কেবল এটি স্ট্রিং হিসাবে ফর্ম্যাট করুন। (আপনি যদি এটি কোনও বিকল্প রাউন্ডিং পদ্ধতির সাথে প্রদর্শন করতে চান এবং এখানে প্রচুর পরিমাণ রয়েছে তবে আপনার দুটি পদ্ধতির মিশ্রণ করা দরকার need)

>>> "%.2f" % 3.14159
'3.14'
>>> "%.2f" % 13.9499999
'13.95'

এবং সর্বশেষে, যদিও সম্ভবত সবচেয়ে গুরুত্বপূর্ণ, আপনি যদি সঠিক গণিত চান তবে আপনি মোটেও ভাসা চলতে চান না। সাধারণ উদাহরণটি অর্থের সাথে লেনদেন করা হয় এবং 'সেন্ট' একটি পূর্ণসংখ্যা হিসাবে সঞ্চয় করে।


68

নীচের কোডটি ব্যবহার করে দেখুন:

>>> a = 0.99334
>>> a = int((a * 100) + 0.5) / 100.0 # Adding 0.5 rounds it up
>>> print a
0.99

তবে সতর্কতা অবলম্বন করুন, এর মানটি এখনও একটি অনর্থক ভাসমান। এখানে একবার দেখুন - repl.it/LJs (ডান বিভাগের শীর্ষে "রান সেশন" ক্লিক করুন)।
লাইফব্লেন্স

3
আপনি যদি এই পদ্ধতির সাথে যান তবে আরও সঠিক প্রতিনিধিত্বের জন্য আপনার 0.5 টি যুক্ত করা উচিত। int (এ * 100 + 0.5) / 100.0; ম্যাথ.সিল ব্যবহার করা অন্য বিকল্প।
arhuaco

3
@ শশাঙ্কসওয়ান্ট: ঠিক আছে, একটি কিছুর জন্য, যে উত্তরটি উপস্থাপন করা হয়েছে তা গোলাকার নয়, এটি ছিন্ন হয়ে যায়। শেষে অর্ধেক যোগ করার পরামর্শটি গোল হয়ে যাবে তবে তারপরে roundপ্রথম স্থানে ফাংশনটি ব্যবহার করে এটি করার কোনও সুবিধা নেই । অন্য একটি জিনিসের জন্য, কারণ এই সমাধানটি এখনও ভাসমান পয়েন্ট ব্যবহার করে, ওপির মূল সমস্যাটি রয়ে গেছে এমনকি এই "সমাধান" এর "সংশোধন" সংস্করণেও।
জন ওয়াই

3
-1, এটি কেবলমাত্র roundফাংশনটির অপ্রয়োজনীয় পুনরায় বাস্তবায়ন (যা প্রশ্নে ব্যবহৃত হয়েছিল)।
ইন্টারজয়

4
@ ইনটারজয় যা অপরিহার্য, যদি round()ওপি উল্লিখিত হিসাবে কাজ না করে।
পিথিকোস

57

টিএলডিআর;)

ইনপুট / আউটপুটটির বৃত্তাকার সমস্যাটি পাইথন ২.7.০ এবং ৩.১ দ্বারা সুনির্দিষ্টভাবে সমাধান করা হয়েছে ।

একটি সঠিকভাবে গোলাকার নম্বরগুলি পিছনে পিছনে পিছনে রূপান্তরিত করা যায়:
str -> float() -> repr() -> float() ...বা Decimal -> float -> str -> Decimal
স্টোরেজের জন্য দশমিক প্রকারের প্রয়োজন হয় না।


(স্বাভাবিকভাবে, জমে থাকা শেষ বিট ত্রুটিগুলি মুছে ফেলার জন্য বৃত্তাকার সংখ্যার যোগ বা বিয়োগের ফলাফলকে গোল করার প্রয়োজন হতে পারে An স্পষ্টত দশমিক গাণিতিকটি এখনও কার্যকর হতে পারে তবে স্ট্রিংয়ের সাথে রূপান্তর str()(এটি 12 টি বৈধ সংখ্যার সাথে সাথে রয়েছে) ) চূড়ান্ত নির্ভুলতা না থাকলে বা ক্রমাগত গাণিতিক ক্রমের কোনও চূড়ান্ত সংখ্যার প্রয়োজন না হলে সাধারণত যথেষ্ট ভাল if

অসীম পরীক্ষা :

import random
from decimal import Decimal
for x in iter(random.random, None):           # Verify FOREVER that rounding is fixed :-)
    assert float(repr(x)) == x                # Reversible repr() conversion.
    assert float(Decimal(repr(x))) == x
    assert len(repr(round(x, 10))) <= 12      # Smart decimal places in repr() after round.
    if x >= 0.1:                              # Implicit rounding to 12 significant digits
        assert str(x) == repr(round(x, 12))   # by str() is good enough for small errors.
        y = 1000 * x                             # Decimal type is excessive for shopping
        assert str(y) == repr(round(y, 12 - 3))  # in a supermaket with Python 2.7+ :-)

নথিপত্র

রিলিজটি পাইথন ২.7 নোটগুলি দেখুন - অন্যান্য ভাষা চতুর্থ অনুচ্ছেদে পরিবর্তন করে:

ভাসমান-পয়েন্ট সংখ্যা এবং স্ট্রিংগুলির মধ্যে রূপান্তরগুলি এখন বেশিরভাগ প্ল্যাটফর্মগুলিতে সঠিকভাবে গোল হয়। এই রূপান্তরগুলি অনেকগুলি পৃথক স্থানে ঘটে: স্ট্রেট () ফ্লোট এবং জটিল সংখ্যায়; ভাসমান এবং জটিল নির্মাণকারী; সংখ্যার বিন্যাসকরণ; সিরিয়ালাইজেশন এবং ডি-সিরিয়ালাইজেশন marshal, pickleএবং jsonমডিউলগুলি ব্যবহার করে ভাসমান এবং জটিল সংখ্যাগুলি ; পাইথন কোডে ভাসমান এবং কল্পিত আক্ষরিক পার্সিং; এবং দশমিক-থেকে-ফ্ল্যাট রূপান্তর।

এর সাথে সম্পর্কিত, একটি ভাসমান-পয়েন্ট সংখ্যা x এর রিটার () এখন সংক্ষিপ্ততম দশমিক স্ট্রিংয়ের উপর ভিত্তি করে ফলাফল দেয় যা সঠিক বৃত্তাকার (রাউন্ড-অর্ধ-এমনকি-এমনকি রাউন্ডিং মোডের সাথে) এর আওতায় ফিরে x এর গ্যারান্টিযুক্ত । পূর্বে এটি 17 দশমিক অঙ্কের বৃত্তাকার উপর ভিত্তি করে একটি স্ট্রিং দিয়েছে।

সম্পর্কিত সমস্যা


আরও তথ্য:float পাইথন ২.7 এর আগে ফর্ম্যাটিংটি বর্তমানের মতো ছিল numpy.float64। উভয় প্রকার 52 বিট ম্যান্টিসার সাথে একই 64 বিট আইইইই 754 ডাবল নির্ভুলতা ব্যবহার করে । একটি বড় পার্থক্য হ'ল np.float64.__repr__অত্যধিক দশমিক সংখ্যার সাথে প্রায়শই ফর্ম্যাট করা হয় যাতে কোনও বিট হারাতে না পারে তবে 13.949999999999999 এবং 13.95000000000000001 এর মধ্যে কোনও বৈধ আইইইই 754 নম্বর বিদ্যমান নেই। ফলাফলটি দুর্দান্ত নয় এবং রূপান্তরটি repr(float(number_as_string))নমপির সাথে বিপরীত নয়। অন্য দিকে:float.__repr__ফর্ম্যাট করা হয় যাতে প্রতিটি সংখ্যা গুরুত্বপূর্ণ; ক্রমটি ফাঁক ছাড়াই এবং রূপান্তরটি उलटযোগ্য। সহজভাবে: যদি আপনার কাছে সম্ভবত একটি নম্পি.ফ্লোএট number৪ নম্বর থাকে তবে এটি সংখ্যার প্রসেসরের জন্য নয়, মানুষের জন্য ফরম্যাট করার জন্য এটিকে স্বাভাবিক ফ্লোটে রূপান্তর করুন, অন্যথায় পাইথন ২.7+ এর সাথে আর কিছুই করার দরকার নেই।


কেন ডাউনভোটেড? প্রশ্নটি পাইথন float(ডাবল নির্ভুলতা) এবং সাধারণ roundসম্পর্কে ছিল, নাম্পি.ডুবল এবং তার স্ট্রিংতে রূপান্তর সম্পর্কে নয়। পাইথন ২.7-এর চেয়ে সমতল পাইথন রাউন্ডিং সত্যিই ভাল করা যায় না। সর্বাধিক উত্তরগুলি ২.7 এর আগে লেখা হয়েছিল, তবে সেগুলি বাতিল করা হয়েছে, যদিও তারা মূলত খুব ভাল ছিল। এই আমার উত্তর কারণ।
hynekcer

53 টি বিট যখন আপনি "লুকানো বিট" অন্তর্ভুক্ত করেন যা 1"ধীরে ধীরে আন্ডারফ্লো" ব্যতীত স্পষ্টতই হয়।
রিক জেমস

এটি রাউন্ডের দোষ নয়, এটি প্রদর্শন দোষ।
রিক জেমস

হ্যাঁ, এটি সর্বজনবিদিত। আমি পাইথন ২.7 প্রকাশের নোটে বা আমার পাঠ্যে বা কিছুতেই কিছু না বলে আপত্তি জানালে আমি একটি প্রসঙ্গ মিস করছি। এই প্রশ্নের প্রয়োজনের চেয়ে এটি আরও জটিল। এটি যুক্ত করা উচিত যে নির্দিষ্ট 32-বিট ইন্টেল চিপগুলিতে রাউন্ডিং বাগের কারণে পাইথন ২.7 এও স্ট্রিং থেকে ফ্লোটে রূপান্তরটি স্থির করা হয়েছে এবং "রাউন্ড () ফাংশনটিও এখন সঠিকভাবে গোল হয়েছে।" ( রিলিজ নোটস - 3.1 বৈশিষ্ট্যগুলি 2.7 এ ব্যাকপোর্ট করা হয়েছে )। আপনি কি একমত হতে পারেন?
hynekcer

1
উফ, a*bবনাম ছিল b*a। লিঙ্কগুলির জন্য ধন্যবাদ - নস্টালজিয়া।
রিক জেমস 20

52

পাইথন <3 (উদাহরণস্বরূপ 2.6 বা 2.7) এর সাথে এটি করার দুটি উপায় রয়েছে।

# Option one 
older_method_string = "%.9f" % numvar

# Option two (note ':' before the '.9f')
newer_method_string = "{:.9f}".format(numvar)

তবে মনে রাখবেন যে পাইথন সংস্করণগুলির জন্য 3 টি উপরে (উদাহরণস্বরূপ 3.2 বা 3.3), বিকল্প দুটি পছন্দ করা হয়েছে

বিকল্প দুটি বিষয়ে আরও তথ্যের জন্য, আমি এই লিঙ্কে সুপারিশ স্ট্রিং পাইথন নথিপত্র থেকে ফর্ম্যাটিং

এবং বিকল্প বিকল্পটির আরও তথ্যের জন্য, এই লিঙ্কটি যথেষ্ট হবে এবং বিভিন্ন পতাকার তথ্য রয়েছে

তথ্যসূত্র: ভাসমান পয়েন্ট সংখ্যাটি একটি নির্দিষ্ট নির্ভুলিতে রূপান্তর করুন এবং তারপরে স্ট্রিংয়ে অনুলিপি করুন


আপনি কিভাবে একটি পূর্ণসংখ্যার প্রতিনিধিত্ব করবেন? আমি যদি "{i3}"। ফর্ম্যাট (numvar) ব্যবহার করি তবে আমি একটি ত্রুটি পাই।
স্কাইটাক্স

এটি আমার অর্থ যা: যদি numvar=12.456, তবে "{:.2f}".format(numvar)ফলন হয় 12.46তবে "{:2i}".format(numvar)একটি ত্রুটি দেয় এবং আমি প্রত্যাশা করি 12
স্কাইটাক্স


47

এখানে কেউ এখনও এটি উল্লেখ করেছে বলে মনে হয় না, তাই পাইথন ৩.6 এর এফ-স্ট্রিং / টেমপ্লেট-স্ট্রিং ফর্ম্যাটে একটি উদাহরণ দিতে পারি, যা আমার মনে হয় সুন্দরভাবে ঝরঝরে:

>>> f'{a:.2f}'

এটি অপারেটরগুলির সাথে এবং প্যারেনগুলির প্রয়োজন না হওয়ার সাথে দীর্ঘতর উদাহরণগুলির সাথেও খুব ভালভাবে কাজ করে:

>>> print(f'Completed in {time.time() - start:.2f}s')


29

পাইথন ২.7 এ:

a = 13.949999999999999
output = float("%0.2f"%a)
print output

1
এটি কিছুতেই সহায়তা করে না। outputহয়েছে সঠিক একই হিসাবে মান aযাতে আপনি যেমন ভাল লেখা থাকতে পারে, print aপরিবর্তে print outputগত লাইনে।
মার্ক ডিকিনসন

@ মার্কডিকিনসন আপনি কি আবার চেষ্টা করতে পারেন? কারণ এটি আমার সংকলনে প্রত্যাশার মতো চলছে is
শশাঙ্ক সিং

1
আপনি আমার বক্তব্য মিস করছেন। হ্যাঁ, আপনার কোড মুদ্রণ 13.95। তবে পাইথন ২.7- print aএর এই নির্দিষ্ট মানটির জন্য aএটি করা যায়, সুতরাং বিন্যাসের ধাপের বিন্দুটি কী ছিল তা সত্যই পরিষ্কার নয়।
মার্ক ডিকিনসন

@ মার্কডিকিনসন আমি কোডটি সম্পাদনা করেছি। আমি সম্মত হই যে 'মুদ্রণ এ' "মুদ্রণ আউটপুট" হিসাবে একই মান মুদ্রণ করে না। তবে আপনি যদি "a == আউটপুট" তুলনা করেন তবে ফলাফলটি "মিথ্যা" হবে কারণ বিন্যাসের ধাপটি ভাসমান মান "এ" থেকে দুই দশমিক পয়েন্টের বাইরে চলে।
শশাঙ্ক সিং

1
আপনি a == outputযে কোডটি দেখান সেটির জন্য আপনি কি আসলে চেষ্টা করেছিলেন? এটি Trueআমার জন্য দেয় এবং আমিও সন্দেহ করি এটি আপনার পক্ষেও হয়েছে।
মার্ক ডিকিনসন

22

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

>>> 0.1
0.10000000000000001

আপনি round() ফাংশনটি ব্যবহার করে এটি প্রত্যাশা করা একক অঙ্কে ফিরে কাটাতে প্ররোচিত হতে পারেন। তবে এতে কোনও পার্থক্য নেই:

>>> round(0.1, 1)
0.10000000000000001

সমস্যাটি হল যে বাইনারি ভাসমান পয়েন্টের জন্য সঞ্চিত “0.1” এটি ইতিমধ্যে সর্বোত্তম সম্ভাব্য বাইনারি অনুমানের পরিমাণ ছিল 1/10, সুতরাং এটির আবার গোল করার চেষ্টা এটি আরও ভাল করে তুলতে পারে না: এটি ইতিমধ্যে যেমনটি পেয়েছিল তেমন ভাল ছিল।

আর একটি পরিণতি হ'ল যেহেতু 0.1 হুবহু নয় 1/10, দশটি মানের 0.1যোগফলগুলি ঠিক ফলন করতে পারে না 1.0:

>>> sum = 0.0
>>> for i in range(10):
...     sum += 0.1
...
>>> sum
0.99999999999999989

আপনার সমস্যার একটি বিকল্প এবং সমাধান decimalমডিউলটি ব্যবহার করা হবে ।




11

দশমিক বস্তু এবং বৃত্তাকার () পদ্ধতির সংমিশ্রণটি ব্যবহার করুন।

Python 3.7.3
>>> from decimal import Decimal
>>> d1 = Decimal (13.949999999999999) # define a Decimal
>>> d1 
Decimal('13.949999999999999289457264239899814128875732421875')
>>> d2 = round(d1, 2) # round to 2 decimals
>>> d2
Decimal('13.95')

7

পাইথন এবং জাভাস্ক্রিপ্টের মতো টাইপ-ডায়নামিক ভাষাগুলিতে ভাসমান পয়েন্টটি ঠিক করার জন্য, আমি এই কৌশলটি ব্যবহার করি

# For example:
a = 70000
b = 0.14
c = a * b

print c # Prints 980.0000000002
# Try to fix
c = int(c * 10000)/100000
print c # Prints 980

আপনি নিম্নলিখিত হিসাবে দশমিক ব্যবহার করতে পারেন:

from decimal import *
getcontext().prec = 6
Decimal(1) / Decimal(7)
# Results in 6 precision -> Decimal('0.142857')

getcontext().prec = 28
Decimal(1) / Decimal(7)
# Results in 28 precision -> Decimal('0.1428571428571428571428571429')

1
getcontext().prec = 6কেবলমাত্র ফাংশনের সুযোগ বা সমস্ত জায়গার জন্য কাজ করে?
জুলিও মেরিনস 4-12 ই

1
প্রসংগগুলি গাণিতিক ক্রিয়াকলাপের জন্য পরিবেশ। তারা নির্ভুলতা পরিচালনা করে, রাউন্ডিংয়ের জন্য বিধিবিধান নির্ধারণ করে, কোন সংকেতকে ব্যতিক্রম হিসাবে বিবেচনা করা হয় তা নির্ধারণ করে এবং এক্সপোজারগুলির জন্য সীমার সীমাবদ্ধ করে। প্রতিটি থ্রেডের নিজস্ব বর্তমান প্রসঙ্গ রয়েছে @ জুলিওমারিনস
সিয়ামন্ড

7
from decimal import Decimal


def round_float(v, ndigits=2, rt_str=False):
    d = Decimal(v)
    v_str = ("{0:.%sf}" % ndigits).format(round(d, ndigits))
    if rt_str:
        return v_str
    return Decimal(v_str)

ফলাফল:

Python 3.6.1 (default, Dec 11 2018, 17:41:10)
>>> round_float(3.1415926)
Decimal('3.14')
>>> round_float(3.1445926)
Decimal('3.14')
>>> round_float(3.1455926)
Decimal('3.15')
>>> round_float(3.1455926, rt_str=True)
'3.15'
>>> str(round_float(3.1455926))
'3.15'

6
orig_float = 232569 / 16000.0

14.5355625

short_float = float("{:.2f}".format(orig_float)) 

14,54



4

এটি 1,2,3 এর মতো সহজ:

  1. দশমিক ব্যবহার ফাস্ট সঠিকভাবে-বৃত্তাকার দশমিক ফ্লোটিং পয়েন্ট গাণিতিক জন্য মডিউল:

    D = ডেসিমাল (10000000.0000009)

বৃত্তাকার অর্জন:

   d.quantize(Decimal('0.01'))

সঙ্গে ফলাফল হবে Decimal('10000000.00')

  1. উপরে DRY করুন:
    def round_decimal(number, exponent='0.01'):
        decimal_value = Decimal(number)
        return decimal_value.quantize(Decimal(exponent))

অথবা

    def round_decimal(number, decimal_places=2):
        decimal_value = Decimal(number)
        return decimal_value.quantize(Decimal(10) ** -decimal_places)
  1. এই উত্তর upvote :)

PS: অন্যের সমালোচনা: ফর্ম্যাটিংটি গোল হয় না।


2

কোনও সংখ্যাকে একটি রেজোলিউশনে গোল করার জন্য, সর্বোত্তম উপায়টি হল নিম্নলিখিতটি যা কোনও রেজোলিউশনের সাথে কাজ করতে পারে (দুটি দশমিক বা এমনকি অন্যান্য পদক্ষেপের জন্য 0.01):

>>> import numpy as np
>>> value = 13.949999999999999
>>> resolution = 0.01
>>> newValue = int(np.round(value/resolution))*resolution
>>> print newValue
13.95

>>> resolution = 0.5
>>> newValue = int(np.round(value/resolution))*resolution
>>> print newValue
14.0

অজগর 3.4.3 এবং ছদ্মবেশী 1.9.1 এ আমার জন্য কাজ করে না? >>> এনপি হিসাবে নাম্বার আমদানি করুন >>> রেস = 0.01 >>> মান = 0.184 >>> এনপি.আউন্ড (মান / রেজোল) * পুনঃ 0.17999999999999999
সিজেটলিন

1
ডকুমেন্টেশন সন্ধানে আমি দেখছি সমস্যাটি numpy.roundনির্ভুলতা / নির্ভুলতা থেকে আসে । সুতরাং এটির সাথে রেজোলিউশনের গুণমানের পূর্বে এটি হিসাবে সংজ্ঞা দেওয়া দরকার। আমি কোড আপডেট করেছি। এটার জন্য ধন্যবাদ!
ইবলাসি

শুধুমাত্র প্রয়োজনীয় হ'ল numpy.float64এনপি.গ্রাউন্ডের ফলাফলটি floatকেবল রূপান্তর করতে বা ব্যবহার করতে round(value, 2)। কোনও বৈধ আইইইই 754 নম্বর 13.949999999999999 (= 1395 / 100.) এবং 3.950000000000001 (= 1395 * .01) এর মধ্যে বিদ্যমান নেই। আপনি কেন মনে করেন যে আপনার পদ্ধতিটি সর্বোত্তম? আসল মান 13.94999999999999999289 (= মান = রাউন্ড (মান, 2)) আপনার 13.95000000000000178 (এনপি.ফ্লোয়াট96 দ্বারা মুদ্রিত) এর চেয়ে আরও সঠিক। নম্পুদের জন্য আরও তথ্য এখন আমার উত্তরে যুক্ত করা হয়েছে যে আপনি সম্ভবত ভুলের দ্বারা কম হয়ে গেছেন। এটি মূলত নির্লিপ্ত সম্পর্কে ছিল না।
hynekcer

@ হাইঙ্কার আমার উত্তরটি সবচেয়ে ভাল বলে আমি মনে করি না। কেবলমাত্র সীমা ভাসনের উদাহরণটি দশমিক দশকে যুক্ত করতে চেয়েছিল তবে সংজ্ঞায়িত রেজোলিউশনের নিকটতম। আপনি যেমন বলেছিলেন আমি তা পরীক্ষা করে দেখেছি যে এর পরিবর্তে intআপনি float@ সেজিটলিন উদাহরণের জন্যও ব্যবহার করতে পারেন । আপনার অতিরিক্ত মন্তব্যের জন্য আপনাকে ধন্যবাদ। (দুঃখিত তবে আমি আপনাকে
নিম্নচ্যুত

সংখ্যাগত প্রসেসিংয়ের জন্য সম্পূর্ণ নতুন নির্ভরতা যুক্ত করা (প্যান্ডাস) "সেরা উপায়"?
হিজাজ্মান

1

ল্যাম্বদা এক্স, এন: ইন্ট (এক্স * 10 এন + .5) / 10 এন বহু বছরের জন্য বহু ভাষায় আমার জন্য কাজ করেছে ।


-13

আমি যে পদ্ধতিটি ব্যবহার করি তা হ'ল স্ট্রিং স্লাইসিং। এটি তুলনামূলক দ্রুত এবং সহজ।

প্রথমে ফ্লোটটিকে স্ট্রিংয়ে রূপান্তর করুন, আপনি যে দৈর্ঘ্যের হতে চান তা চয়ন করুন।

float = str(float)[:5]

উপরের একক লাইনে আমরা মানটিকে একটি স্ট্রিংয়ে রূপান্তর করেছি, তারপরে স্ট্রিংটিকে কেবল তার প্রথম চারটি অঙ্ক বা অক্ষরে (অন্তর্ভুক্ত) রেখেছি।

আশা করি এইটি কাজ করবে!


2
দয়া করে একাধিক প্রশ্নের একই উত্তর পোস্ট করবেন না।
ভল্টাহ

18
বাহ ... টিডিএইচ ... দয়া করে কোনও অ্যাকাউন্টিং সফ্টওয়্যার তৈরি করবেন না ... সংখ্যাটি যদি 113.94 হয় তবে কি হবে ?? এর ফলস্বরূপ 113.9 ... 0.04 নিখোঁজ রেখে যাবে .... এছাড়াও এর ইতিমধ্যে 5 বছরেরও আগে উত্তর রয়েছে ....
রাগান্বিত 84
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.