JavaRush /Java блогу /Random-KY /Java тилиндеги сандарды тегеректөө

Java тилиндеги сандарды тегеректөө

Группада жарыяланган
Ондук тактыкты талап кылган туюнтмаларды эсептөөдө калкыма чекиттик сандар (float, double) колдонулат. Бухгалтердик эсепке жана башка эсептөө операцияларына көбүнчө жогорку тактык керек. Java тorнде тегеректөө сандары - 1Бирок биз ар дайым ондук чекиттен кийин сандардын узун "куйругу" керекпи? Балким, биз үчүн үч реалдуу бөлүктүн тактыгы жетиштүүбү? Ал эми бул вариант бизди канааттандырса, тегеректөөнү кантип туура аткаруу керек? Бүгүн биз так ушул жөнүндө сүйлөшөбүз: Java тorнде сандарды тегеректөө жолдорун карап чыгабыз .

Сап форматы

Биринчи ыкма катары, биз эки тегеректөөнү карап чыгабыз:
double value = 34.766674;
String result = String.format("%.3f",value);
System.out.print(result);//  34,767
Натыйжада, биз 34766674 калкыма чекитибизди 3 ондук бөлүктүн тактыгы менен форматтайбыз , анткени форматтоо нускамаларында үч ондук белгини "%.3f" белгилегенбиз. Өз кезегинде, %f сапты форматтоодо калкыма чекиттин түрүн көрсөтөт. сандар, анын ичине Java тorндеги double жана float маалымат түрү кирет . Жогорудагы мисалда биз натыйжадагы маанини консолго чыгарабыз. Эми суроо: муну кантип кыскарта алабыз? Бул жөнөкөй: сиз өз кезегинде printf колдонушуңуз керек. Бул формат + басып чыгаруу. Натыйжада, мурунку Биздин мисал төмөндөйт:
double value = 34.766674;
System.out.printf("%.3f",value);
Бул ыкмадан тышкары, PrintStream классынын сырткы инстанциясында дагы окшош иштеген формат ыкмасы бар:
double value = 34.766674;
System.out.format("%.3f",value);
Tagеректөө HALF_UP режиминде ишке ашат - чекке жакыныраак санга карай (0 же 10го чейин). Эгерде бул сандар бирдей аралыкта болсо (5 болгон учурда), анда тегеректөө жүргүзүлөт. Мисал:
String firstResult = String.format("%.3f",7.0004);// 7,000
String secondResult = String.format("%.3f",7.0005);// 7,001
String thirdResult = String.format("%.3f",7.0006);// 7,001
Tagеректөө режимдерин төмөндө кененирээк талкуулайбыз. Java тorнде тегеректөө сандары - 2

DecimalFormat

Дагы бир вариант - DecimalFormat классын колдонуу . Ал бүтүн же калкыма чекиттүү сан болобу, Javaдагы каалаган санды форматтоо үчүн иштелип чыккан. Биз DecimalFormat түзгөндө , биз аны формат сабын өткөрө алабыз. Ал киргизүү үчүн канча ондук белгини форматтоо керектигин көрсөтөт. Биздин мисал DecimalFormat колдонууда ушундай болот :
double value = 34.766674;
DecimalFormat decimalFormat = new DecimalFormat( "#.###" );
String result = decimalFormat.format(value);
System.out.print(result);//34,767
#.### сызыгы - бул берилген маанини 3 ондук орунга форматтап жатканыбызды көрсөткөн үлгү. DecimalFormat an objectи түзүлгөндөн кийин үлгүнү өзгөртүү үчүн анын applicationPattern жана applyLocalizedPattern ыкмаларын колдонсоңуз болот :
DecimalFormat decimalFormat = new DecimalFormat("#.###");
decimalFormat.applyPattern("#.#");
decimalFormat.applyLocalizedPattern("#.#####");
Бирок бүгүн биз тегеректөө жөнүндө айтып жатабыз, туурабы? Көрсөтүлгөн үлгүдөн ашкан ондук бөлүктөрү бар санды кыскартууда, DecimalFormat акыркы кыскартылган сан 5тен чоң болсо, санды өйдө тегеретет. Бирок эгер сан 5 болсочы? Көрсө, ал эң жакын бүтүн сандардын ортосунда так турат. Анда эмне? Бул учурда мурунку сан эске алынат. Эгерде ал жуп болсо, тегеректөө жүргүзүлөт:
DecimalFormat decimalFormat = new DecimalFormat("#.###");
String result = decimalFormat.format(7.4565);
System.out.println((result));// 7,457
Так болсо, ал аткарылbyte:
DecimalFormat decimalFormat = new DecimalFormat("#.###");
String result = decimalFormat.format(7.4575);
System.out.println((result));// 7,457
String.format() жана DecimalFormat.format() аркылуу калкыма чекиттерди форматтоо ортосунда бир аз айырма бар. Биринчиси, бөлчөк бөлүгү жок болсо да, ар дайым арткы нөлдөрдү басып чыгарат. Мисалга:
String firstResult = String.format("%.3f", 7.000132);
System.out.println((firstResult)); // 7.000

DecimalFormat decimalFormat = new DecimalFormat("#.###");
String secondResult = decimalFormat.format(7.000132);
System.out.println((secondResult));  // 7
Көрүнүп тургандай, 7.000132 санын үч ондук орунга форматтоодо String's format() методу 7.000 чыгарат, ал эми DecimalFormatдын format() ыкмасы 7. Башкача айтканда, сиз String.format() же DecimalFormat. format() тандай аласыз. ) арткы нөлдөрдүн кереги барбы же жокпу, жараша. Жогоруда айтылган ыкмаларды колдонуу менен биз сап түрүндө натыйжа алдык. Келгиле, так сандык маанилерди кайтаруунун жолдорун карап көрөлү.

Математика

Сандар менен ар кандай арифметикалык операцияларга ылайыкташтырылган атайын классты - Математиканы айтпай коюуга болбойт . Java тorнде тегеректөө сандары - 3Бул класста тегеректөө ыкмалары да бар, бирок буга чейин сүрөттөлгөндөрдөн айырмаланып, алар белгилүү бир сандагы ондук орундарды коюуга мүмкүндүк бербейт, тескерисинче бүтүн санга тегеректөө:
  • Math.ceil() эң жакын бүтүн санга чейин тегеретет, бирок бүтүн сан түрүн эмес, эки эселенген санды кайтарат:

    double value = 34.777774;
    double result = Math.ceil(value);
    System.out.println((result)); //35.0

    Бизде 34.0000000 болсо да, Math.ceil колдонгондон кийин дагы 35.0 алабыз.

    Math.floor() эң жакын бүтүн санга чейин тегеретет, ошондой эле натыйжаны эки эсе кылып кайтарат:

    double value = 34.777774;
    double result = Math.floor(value);
    System.out.println((result)); //34.0

    Дагы бир жолу, бизде 34.999999999 мааниси бар болсо да, Math.floor колдонгондон кийин биз 34.0 алабыз.

  • Math.round () - int натыйжасын берген эң жакын бүтүн санга тегеретет:

    double value = 34.777774;
    int result = Math.round(value);
    System.out.println((result)); //35

    Эгерде биздин сан 34,5 болсо, 35ке тегеректелет, ал эми 34,499дан бир аз аз болсо, анда сан 34кө кыскартылат.

    Бүт реалдуу бөлүгүн жөн эле кесип эмес, бул процессти ондуктардын белгилүү бир санына чейин жөнгө салуу жана ошол эле учурда тегеректөө үчүн, сан 10 ^ n (n даражасына 10) көбөйтүлөт, мында n зарыл болгон ондук белгилердин санына барабар. Андан кийин, математика классынын кээ бир ыкмасы тегеректөө үчүн колдонулат, анан кайра 10^nга бөлүнөт:

    double value = 34.777774;
    double scale = Math.pow(10, 3);
    double result = Math.ceil(value * scale) / scale;
    System.out.println((result)); //34.778

    Math.pow - эки аргумент алат. Биринчиси - бул сан, экинчиси - аны көтөрүү керек болгон күч.

BigDecimal менен тегеректөө

BigDecimal - бул калкыма чекиттер менен иштөөгө мүмкүндүк берген класс. Тактап айтканда, анын негизги өзгөчөлүгү - ал ыктыярдуу узундуктагы бөлчөк сандарды сактай алат (башкача айтканда, сандын диапазонуна чек жок). Мындан тышкары, бул класс арифметикалык иштетүү үчүн ар кандай ыкмаларды, анын ичинде тегеректөөлөрдү сактайт. Бул an objectтин классы конструкторду экиге, калкыма чекиттин санын көрсөтүү үчүн сапка, double жана MathContext ж.б. коюу менен түзүлүшү мүмкүн . MathContext RoundingMode менен изделген маанидеги цифралардын жалпы санын сүрөттөгөн сандын айкалышы . Tagеректөө эрежелери RoundingMode: DOWN - нөлгө тегеректөө. UP — нөл режиминен тегеректөө. ШЫП – оң чексиздикке карай тегеректөө. FLOOR - терс чексиздикти көздөй тегеректөө. HALF_UP - Эки кошуна тең бирдей эмес болсо, "жакынкы кошунага" тегеретет (башкача айтканда, тегеректелген сан 5 болгондо). Бул учурда, тегеректөө жүргүзүлөт. HALF_DOWN - "жакынкы кошуна" карай тегеректөө. Эгерде эки кошуна тең бирдей эмес болсо, анда тегеректелет. HALF_EVEN - Эгерде эки кошуна тең бирдей эмес болсо, "жакынкы кошунага" тегеретет. Бул учурда, жуп кошунага тегеретиңиз (жогоруда сүрөттөлгөн DecimalFormatтагыдай). NENEESSARY - Суралган операциянын туура натыйжасы бар экенин тастыктоо үчүн колдонулат. Ошондуктан, тегеректөө талап кылынbyte. Мисал:
MathContext context = new MathContext(5, RoundingMode.HALF_UP);
double value = 34.777554;
BigDecimal result = new BigDecimal(value, context);
System.out.println(result); //34.778
Конструктордо тегеректөө эрежесин коюу мүмкүнчүлүгүнөн тышкары, BigDecimal инстанция түзүлгөндөн кийин тегеректөө режимин коюуга мүмкүндүк берет. Бул үчүн, setScale ыкмасын колдонуңуз , анда ондук орундардын санын жана тегеректөө эрежелерин коюшуңуз керек:
double value = 34.777554;
BigDecimal result = new BigDecimal(value);
result = result.setScale(3, RoundingMode.DOWN);
System.out.println(result); //34.777
BigDecimal ошондой эле тегеректөө режимин коюу үчүн иштелип чыккан ички int өзгөрмөлөргө ээ ( ROUND_DOWN , ROUND_CEILING , ROUND_FLOOR ...) Булар RoundingMode классында берилген тегеректөө эрежелерине окшош жана setScaleде да ушундай эле колдонулат :
BigDecimal result = new BigDecimal(value);
result = result.setScale(3, BigDecimal.ROUND_DOWN);
Бул макалада BigDecimal классы жөнүндө көбүрөөк окуңуз .
Комментарийлер
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION