Jak uzyskać liczby po przecinku?


Odpowiedzi:


28

Łatwe podejście dla Ciebie:

number_dec = str(number-int(number))[1:]

31
Ćwiczenie dla czytelnika: spraw, by działało dla liczb większych lub równych 10
intuicyjnie

11
number_dec = str(number-int(number)).split('.')[1]
Ryan Allen

28
Głosuj przeciw, ponieważ jest to niepotrzebnie skomplikowane podejście. Odpowiedź, której szukałem, była następną odpowiedzią, 5.55 % 1która jest również bardziej użyteczną odpowiedzią - można zastosować podejście dzielenia modulo w wielu językach, podczas gdy powyższa odpowiedź jest specyficzna dla Pythona.
Gulasz

3
UWAGA: To rozwiązanie zwraca ciąg znaków zawierający kropkę ( .55), czego możesz się nie spodziewać ze względu na tytuł pytania!
T. Christiansen

9
str(5.55 - int(5.55))[1:]zwraca .5499999999999998zamiast .55wymienionego w pytaniu.
Cristian Ciupitu

201
5.55 % 1

Pamiętaj, że nie pomoże ci to w problemach z zaokrąglaniem zmiennoprzecinkowym. To znaczy, możesz otrzymać:

0.550000000001

Lub w przeciwnym razie trochę poniżej 0,55, którego oczekujesz.


7
Co do tego modf, może też wkręcić precyzję: math.modf(5.55)zwróci (0.5499999999999998, 5.0).
bereal

1
czy ktoś wie, która operacja byłaby szybsza, ta metoda opisana powyżej, czy: float b = a - int (a)? Podejrzewam później, ale chciałem sprawdzić, czy jest potwierdzenie
hokkuk

5
Na Raspberry Pi ta metoda x%1była prawie dwukrotnie szybsza niż metody x-int(x)i modf(x)[0](czasy 980ns, 1,39us i 1,47us uśrednione dla 1000000 uruchomień). Moja wartość xzawsze była pozytywna, więc nie musiałem się o to martwić.
coderforlife

Zdecydowanie praca modułu jest szybsza. Nie musi wyszukiwać nazw. Natomiast wywołanie funkcji int wyszukuje zmienne globalne.
Enrico Borba

mieć ochotę nie tylko na frac ()
mckenzm

155

Użyj modf :

>>> import math
>>> frac, whole = math.modf(2.5)
>>> frac
0.5
>>> whole
2.0

2
Dobre rozwiązanie, ale math.modf(2.53) = (0.5299999999999998, 2.0)oczekiwana odpowiedź to 0,53
Lord Loh.

4
@LordLoh. dzieje się tak z powodu zaokrąglania zmiennoprzecinkowego i będzie miało miejsce w przypadku każdej metody.
Rena

@LordLoh. Spróbuj użyć round (0.5299999999999998, 2), aby uzyskać 0.53 Innym sposobem jest użycie pakietu dziesiętnego z dziesiętnego. docs.python.org/2/library/decimal.html
SirJ

57

Co powiesz na:

a = 1.3927278749291
b = a - int(a)

b
>> 0.39272787492910011

Lub używając numpy:

import numpy
a = 1.3927278749291
b = a - numpy.fix(a)

33

Używając decimalmodułu z biblioteki standardowej, możesz zachować oryginalną precyzję i uniknąć problemów z zaokrąglaniem zmiennoprzecinkowym:

>>> from decimal import Decimal
>>> Decimal('4.20') % 1
Decimal('0.20')

Jak zauważa kindall w komentarzach, musisz najpierw przekonwertować natywne s na ciągi znaków.float


Z korzyścią dla oryginalnego pytającego: zmiennoprzecinkowe muszą zostać przekonwertowane na łańcuchy, zanim będzie można je przekonwertować na liczby dziesiętne. Więc jeśli masz n = 5.55, n jest liczbą zmiennoprzecinkową i powinieneś zrobić, Decimal(str(n)) % 1aby uzyskać część ułamkową. (Nie jest to konieczne, jeśli masz liczbę całkowitą, ale to nie boli.)
kindall

2
@intuited: Nie musi to być dziesiętne, działa również dla float: 10.0/3 % 1przynajmniej w moim systemie
aherok

2
Możesz użyć from_float zamiast używać łańcucha. d = Decimal.from_float (1.2)
Matthew Purdon

@intuited Jak uzyskać część dziesiętną jako liczbę całkowitą? Próbowałem metod to_integer (), ale typ jest nadal Decimal.
D1X

1
@MatthewPurdon - Jeśli użyjesz Decimal.from_float(1.2)(które można teraz zapisać jako Decimal(1.2)), będziesz mieć zaokrąglone problemy, których próbowała uniknąć ta odpowiedź.
John Y


5

podobnie jak przyjęta odpowiedź, jeszcze prostszym podejściem byłoby użycie łańcuchów

def number_after_decimal(number1):
    number = str(number1)
    if 'e-' in number: # scientific notation
        number_dec = format(float(number), '.%df'%(len(number.split(".")[1].split("e-")[0])+int(number.split('e-')[1])))
    elif "." in number: # quick check if it is decimal
        number_dec = number.split(".")[1]
    return number_dec

number = 5.55; "." in numberdaje TypeError: argument of type 'float' is not iterable. A co byś zrobił, gdybyś number = 1e-5?
Mark Dickinson

@mark pytanie brzmi: Jak uzyskać liczby po przecinku? więc użytkownik oczekuje liczby zmiennoprzecinkowej w notacji dziesiętnej (nie naukowej), dodałem też blok dla notacji naukowej
yosemite_k

Liczba to liczba; jest to tylko reprezentacja liczby, która może być zapisana w notacji naukowej. Więc „float w notacji dziesiętnej” nie ma tu większego sensu; zanim Python to zobaczy, jest to tylko float; Python nie posiada żadnej wiedzy o tym, w jakim formacie został pierwotnie wyrażony. Mój number = 1e-5przykład odnosi się równie dobrze do number = 0.00001: strreprezentacja liczby jest w notacji naukowej. Będziesz mieć do czynienia z e+, jak i e-, nawiasem mówiąc.
Mark Dickinson

4
import math
orig = 5.55
whole = math.floor(orig)    # whole = 5.0
frac = orig - whole         # frac = 0.55

>>> frac 0.5499999999999998
macm

4
>>> n=5.55
>>> if "." in str(n):
...     print "."+str(n).split(".")[-1]
...
.55

2
Jest to w porządku w przypadku liczb z odmian ogrodowych, ale nie działa tak dobrze w przypadku liczb wystarczająco dużych (lub małych), aby wymagać notacji naukowej.
kindall

2

Oto rozwiązanie, które wypróbowałem:

num = 45.7234
(whole, frac) = (int(num), int(str(num)[(len(str(int(num)))+1):]))

2

Czasami liczą się zera końcowe

In [4]: def split_float(x):
   ...:     '''split float into parts before and after the decimal'''
   ...:     before, after = str(x).split('.')
   ...:     return int(before), (int(after)*10 if len(after)==1 else int(after))
   ...: 
   ...: 

In [5]: split_float(105.10)
Out[5]: (105, 10)

In [6]: split_float(105.01)
Out[6]: (105, 1)

In [7]: split_float(105.12)
Out[7]: (105, 12)

co to robi dla 0,000005?
Aditya Patnaik

2

Używając prostego dzielenia przez operatora „/” i podziału „//” , można łatwo uzyskać część ułamkową dowolnej liczby zmiennoprzecinkowej.

number = 5.55

result = (number/1) - (number//1)

print(result)

1

Użyj podłogi i odejmij wynik od oryginalnej liczby:

>> import math #gives you floor.
>> t = 5.55 #Give a variable 5.55
>> x = math.floor(t) #floor returns t rounded down to 5..
>> z = t - x #z = 5.55 - 5 = 0.55

5
Jeśli masz zamiar import math, dlaczego po prostu nie użyć math.modf()?
ire_and_curses,

@ire_and_curses: Podaję alternatywne rozwiązanie problemu.

1
floor robi to samo, co rzutowanie na int, więc może zastąpić math.floor (t) int (t)
QuantumKarl

@QuantumKarl Nie, są różne. math.floor(-1.1) == -2ale int(-1.1) == -1. Chociaż w przypadku tego pytania użycie intjest bardziej poprawne.
Lambda Fairy

1

Liczby zmiennoprzecinkowe nie są przechowywane w formacie dziesiętnym (podstawa 10). Przeczytaj dokumentację Pythona na ten temat, aby upewnić się, dlaczego. Dlatego uzyskanie reprezentacji o podstawie 10 z liczby zmiennoprzecinkowej nie jest zalecane.

Teraz są narzędzia, które umożliwiają przechowywanie danych liczbowych w formacie dziesiętnym. Poniżej przykład z wykorzystaniem Decimalbiblioteki.

from decimal import *

x = Decimal('0.341343214124443151466')
str(x)[-2:] == '66'  # True

y = 0.341343214124443151466
str(y)[-2:] == '66'  # False

1

Przykład:

import math
x = 5.55
print((math.floor(x*100)%100))

To da ci dwie liczby po przecinku, 55 z tego przykładu. Jeśli potrzebujesz jednej liczby, zmniejsz o 10 powyższe obliczenia lub zwiększ w zależności od tego, ile liczb chcesz po przecinku.


Jest to miłe, ponieważ zwraca wartość nieułamkową, ale przerywa na liczbach ujemnych
Meow

Niestety przez większość czasu nie działa. @Meow
Markiz Lorne,


0

Co powiesz na:

a = 1.234
b = a - int(a)
length = len(str(a))

round(b, length-2)

Wynik:
print(b)
0.23399999999999999
round(b, length-2)
0.234

Ponieważ runda jest wysyłana do długości ciągu liczb dziesiętnych („0,234”), możemy odjąć 2, aby nie policzyć „0” i obliczyć żądaną liczbę miejsc dziesiętnych. Powinno to działać w większości przypadków, chyba że masz dużo miejsc po przecinku, a błąd zaokrąglania podczas obliczania b koliduje z drugim parametrem rundy.


Jakieś wyjaśnienie?

0

Możesz spróbować tego:

your_num = 5.55
n = len(str(int(your_num)))
float('0' + str(your_num)[n:])

Wróci 0.55.


0
number=5.55
decimal=(number-int(number))
decimal_1=round(decimal,2)
print(decimal)
print(decimal_1)

wyjście: 0,55


0

Zobacz, co często robię, aby uzyskać liczby po przecinku w Pythonie 3:

a=1.22
dec=str(a).split('.')
dec= int(dec[1])


0

Inną opcją byłoby użycie remodułu z re.findalllub re.search:

import re


def get_decimcal(n: float) -> float:
    return float(re.search(r'\.\d+', str(n)).group(0))


def get_decimcal_2(n: float) -> float:
    return float(re.findall(r'\.\d+', str(n))[0])


def get_int(n: float) -> int:
    return int(n)


print(get_decimcal(5.55))
print(get_decimcal_2(5.55))
print(get_int(5.55))

Wynik

0.55
0.55
5

Jeśli chcesz uprościć / zmodyfikować / zbadać wyrażenie, zostało to wyjaśnione w prawym górnym panelu regex101.com . Jeśli chcesz, możesz również obejrzeć w tym linku , jak to będzie się zgadzać z niektórymi przykładowymi danymi wejściowymi.


Źródło

Jak pozbyć się dodatkowych liczb zmiennoprzecinkowych w odejmowaniu w Pythonie?


0

Odkryłem, że naprawdę duże liczby z naprawdę dużymi częściami ułamkowymi mogą powodować problemy podczas używania modulo 1 do uzyskania ułamka.

import decimal

>>> d = decimal.Context(decimal.MAX_PREC).create_decimal(
... '143000000000000000000000000000000000000000000000000000000000000000000000000000.1231200000000000000002013210000000'
... )
...
>>> d % 1
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
decimal.InvalidOperation: [<class 'decimal.DivisionImpossible'>]

Zamiast tego złapałem integralną część i odjąłem ją najpierw, aby uprościć resztę.

>>> d - d.to_integral()
Decimal('0.1231200000000000000002013210')

0

Kolejny przykład użycia modf

from math import modf
number = 1.0124584

# [0] decimal, [1] integer
result = modf(number)
print(result[0])
# output = 0124584
print(result[1])
# output = 1

0

Rozwiązaniem jest użycie modulo i zaokrąglanie.

import math

num = math.fabs(float(5.55))
rem = num % 1

rnd_by =   len(str(num)) - len(str(int(num))) - 1

print(str(round(rem,rnd_by)))

Twój wynik wyniesie 0,55



-2

Kolejnym szalonym rozwiązaniem jest (bez konwersji w string):

number = 123.456
temp = 1

while (number*temp)%10 != 0:
    temp = temp *10
    print temp
    print number

temp = temp /10
number = number*temp
number_final = number%temp
print number_final
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.