Yüzenleri Pandalar ints dönüştürmek?


230

Bir CSV'den içe aktarılan verilerle çalışıyorum. Pandalar yüzmek için bazı sütunları değiştirdi, bu yüzden şimdi bu sütunlardaki sayılar kayan nokta olarak görüntüleniyor! Ancak, tamsayı olarak veya virgül olmadan görüntülenmelerini istiyorum. Bunları tamsayılara dönüştürmenin veya virgül görüntülememenin bir yolu var mı?


22
Türü değiştirebilirsiniz (eksik değer olmadığı sürece)df.col = df.col.astype(int)
EdChum

Bu soru aynı anda iki sorudur ve bu sorunun başlığı bunlardan sadece birini yansıtmaktadır.
Monica Heddneck

Yukarıdakilere isabet eden ve konseptte yararlı bulan ancak sizin için çalışmayan bir insan için, bu panda X ile python df = df.astype(int)
3.7.5'te

Yanıtlar:


218

Float çıkışını değiştirmek için şunu yapın:

df= pd.DataFrame(range(5), columns=['a'])
df.a = df.a.astype(float)
df

Out[33]:

          a
0 0.0000000
1 1.0000000
2 2.0000000
3 3.0000000
4 4.0000000

pd.options.display.float_format = '{:,.0f}'.format
df

Out[35]:

   a
0  0
1  1
2  2
3  3
4  4

16
Teşekkürler! Bunu to_csv: fin.to_csv ('my_table.csv', float_format = '%. F') içinde ayarladım. İşe yaradı!
MJP

4
Pandaların en son sürümünde, bir uyarıyı önlemek için astype argümanlarına copy = False eklemeniz gerekir
g.stevo

Yapmaya gerek var df.a = df.a.astype(float)mı? Bu bir kopya yapıyor mu ( copyparametrenin nasıl astype()kullanılacağından emin değil misiniz)? Yine de "yerinde" türünü güncellemek için?
Mr_and_Mrs_D

1
@EdChum, Pandaların türleri dönüştürmesini önlemenin bir yolu var mı? Örneğin DF.({'200': {'#': 354, '%': 0.9971830985915493}, '302': {'#': 1, '%': 0.0028169014084507044}}) , # işlevinin kayan noktaya dönüştürüldüğünü ve sütun değil satır olduklarını unutmayın. çünkü her biri Seriestek bir üniforma tipini saklayabilen bir ürün?
alancalvitti

@alancalvitti Burada değerleri veya neyi korumak niyetiniz dtypenedir? Öyleyse, dtypebu sütunları dtype objectkarışmasına izin verecek şekilde oluşturmanız gerekiyorsa , aksi takdirde tavsiyem sadece şamandıra kullanmak ve karşılaştırma yaparken kullanınnp.isclose
EdChum

180

pandas.DataFrame.astype(<type>)Sütun türlerini işlemek için işlevi kullanın .

>>> df = pd.DataFrame(np.random.rand(3,4), columns=list("ABCD"))
>>> df
          A         B         C         D
0  0.542447  0.949988  0.669239  0.879887
1  0.068542  0.757775  0.891903  0.384542
2  0.021274  0.587504  0.180426  0.574300
>>> df[list("ABCD")] = df[list("ABCD")].astype(int)
>>> df
   A  B  C  D
0  0  0  0  0
1  0  0  0  0
2  0  0  0  0

DÜZENLE:

Eksik değerleri işlemek için:

>>> df
          A         B     C         D
0  0.475103  0.355453  0.66  0.869336
1  0.260395  0.200287   NaN  0.617024
2  0.517692  0.735613  0.18  0.657106
>>> df[list("ABCD")] = df[list("ABCD")].fillna(0.0).astype(int)
>>> df
   A  B  C  D
0  0  0  0  0
1  0  0  0  0
2  0  0  0  0

3
Yaklaşımınızı denedim ve bana bir ValueError veriyor: NA tamsayıya dönüştürülemiyor
MJP

6
Eksik değerler bkz varsa @MJP Sen tamsayıya şamandıradan dizi dönüştürmek olamaz pandas.pydata.org/pandas-docs/stable/... , sen yüzen kullanmak zorunda
EdChum

2
Değerler eksik değil, ancak sütun bilerek her satır için bir değer belirtmiyor. Geçici çözüm bulmanın bir yolu var mı? Bu değerler yabancı anahtar kimlikleri olduğundan ints'e ihtiyacım var.
MJP

4
Tüm NaN'lerin 0.0 ile değiştirildiği bir düzenleme yaptım.
Ryan G

3
Ya da daha iyisi, yalnızca bir CSV'yi değiştiriyorsanız, o zaman: df.to_csv ("path.csv", na_rep = "", float_format = "%. 0f", index = False) Ama bu tüm kayan noktaları düzenleyecektir, FK sütununuzu bir dizeye dönüştürmek, manipülasyonu yapmak ve sonra kaydetmek daha iyi olabilir.
Ryan G

44

Aşağıdaki veri çerçevesi dikkate alındığında:

>>> df = pd.DataFrame(10*np.random.rand(3, 4), columns=list("ABCD"))
>>> print(df)
...           A         B         C         D
... 0  8.362940  0.354027  1.916283  6.226750
... 1  1.988232  9.003545  9.277504  8.522808
... 2  1.141432  4.935593  2.700118  7.739108

Sütun adlarının bir listesini kullanarak, aşağıdakilerle birden çok sütunun türünü değiştirin applymap():

>>> cols = ['A', 'B']
>>> df[cols] = df[cols].applymap(np.int64)
>>> print(df)
...    A  B         C         D
... 0  8  0  1.916283  6.226750
... 1  1  9  9.277504  8.522808
... 2  1  4  2.700118  7.739108

Veya aşağıdakileri içeren tek bir sütun için apply():

>>> df['C'] = df['C'].apply(np.int64)
>>> print(df)
...    A  B  C         D
... 0  8  0  1  6.226750
... 1  1  9  9  8.522808
... 2  1  4  2  7.739108

5
Değerde bir NaN varsa ne olur?
Zhang18

3
@ Zhang18 Bu çözümü denedim ve NaN durumunda şu hatayla karşılaştınız:ValueError: ('cannot convert float NaN to integer', u'occurred at index <column_name>')
enri

3
@enri: Aşağıdaki kodu deneyebilir -df['C'] = df['C'].dropna().apply(np.int64)
vsdaking

12

pandas.DataFrameNaN değerlerine sahip olabileceğiniz göz önüne alındığında, şamandıradan tamsayıya daha fazla sütun dönüştürmek istediğinizde hızlı bir çözümdür .

cols = ['col_1', 'col_2', 'col_3', 'col_4']
for col in cols:
   df[col] = df[col].apply(lambda x: int(x) if x == x else "")

Ben denedim else x)ve else None), ama sonuç hala float numarası, bu yüzden kullandım else "".


""tüm değerlere uygulanacaktırcol
Raheel

Gerekirse, tüm eksik değerlere boş dize ("") uygular, ancak değerlerin geri kalanı tamsayı olur.
Krzysztof Słowiński

Bunun için teşekkürler. Bu .astype () ve .apply (np.int64) çalışmadığında işe yaradı.
Alison S

Bu kibirli hissettiriyor ve mevcut birçok alternatif üzerinde kullanmak için hiçbir neden görmüyorum.
AMC

8

@Ryan G pandas.DataFrame.astype(<type>)yönteminin kullanımından genişleyen errors=ignorebağımsız değişken, yalnızca hata oluşturmayan ve sözdizimini basitleştiren sütunları dönüştürmek için kullanılabilir. Açıkçası, hatalar göz ardı edilirken dikkatli olunmalıdır, ancak bu görev için çok kullanışlı olur.

>>> df = pd.DataFrame(np.random.rand(3, 4), columns=list('ABCD'))
>>> df *= 10
>>> print(df)
...           A       B       C       D
... 0   2.16861 8.34139 1.83434 6.91706
... 1   5.85938 9.71712 5.53371 4.26542
... 2   0.50112 4.06725 1.99795 4.75698

>>> df['E'] = list('XYZ')
>>> df.astype(int, errors='ignore')
>>> print(df)
...     A   B   C   D   E
... 0   2   8   1   6   X
... 1   5   9   5   4   Y
... 2   0   4   1   4   Z

Gönderen pandas.DataFrame.astype docs:

hatalar: {'zam', 'yoksay'}, varsayılan 'zam'

Sağlanan dtype için geçersiz verilerdeki istisnaların kontrolünü sağlama.

  • yükselt: istisnaların yükseltilmesine izin ver
  • yoksay: istisnaları bastır. Hata durumunda orijinal nesneyi döndür

0.20.0 sürümündeki yenilikler.


7
>>> import pandas as pd
>>> right = pd.DataFrame({'C': [1.002, 2.003], 'D': [1.009, 4.55], 'key': ['K0', 'K1']})
>>> print(right)
           C      D key
    0  1.002  1.009  K0
    1  2.003  4.550  K1
>>> right['C'] = right.C.astype(int)
>>> print(right)
       C      D key
    0  1  1.009  K0
    1  2  4.550  K1

5

Tüm kayan sütunları int'e dönüştürmek için

>>> df = pd.DataFrame(np.random.rand(5, 4) * 10, columns=list('PQRS'))
>>> print(df)
...     P           Q           R           S
... 0   4.395994    0.844292    8.543430    1.933934
... 1   0.311974    9.519054    6.171577    3.859993
... 2   2.056797    0.836150    5.270513    3.224497
... 3   3.919300    8.562298    6.852941    1.415992
... 4   9.958550    9.013425    8.703142    3.588733

>>> float_col = df.select_dtypes(include=['float64']) # This will select float columns only
>>> # list(float_col.columns.values)
>>> for col in float_col.columns.values:
...     df[col] = df[col].astype('int64')
>>> print(df)
...     P   Q   R   S
... 0   4   0   8   1
... 1   0   9   6   3
... 2   2   0   5   3
... 3   3   8   6   1
... 4   9   9   8   3

0

Burada, herhangi bir bilgi kaybetmeyen mümkün olan en küçük tamsayı türüne kayan sürgülü basit bir işlev vardır. Örneğin,

  • 100.0 şamandıradan tamsayıya dönüştürülebilir, ancak 99.9 (yuvarlama veya kesilme bilgisini kaybetmeden)

  • Ayrıca, 1.0 int8bilgi kaybetmeden sonuna kadar indirilebilir, ancak 100_000.0 için en küçük tamsayı türüint32

Kod örnekleri:

import numpy as np
import pandas as pd

def float_to_int( s ):
    if ( s.astype(np.int64) == s ).all():
        return pd.to_numeric( s, downcast='integer' )
    else:
        return s

# small integers are downcast into 8-bit integers
float_to_int( np.array([1.0,2.0]) )
Out[1]:array([1, 2], dtype=int8)

# larger integers are downcast into larger integer types
float_to_int( np.array([100_000.,200_000.]) )
Out[2]: array([100000, 200000], dtype=int32)

# if there are values to the right of the decimal
# point, no conversion is made
float_to_int( np.array([1.1,2.2]) )
Out[3]: array([ 1.1,  2.2])

0

İnt'e dönüştürülmesi gereken sütunlar sözlükte aşağıdaki gibi de belirtilebilir

df = df.astype({'col1': 'int', 'col2': 'int', 'col3': 'int'})

-5
>>> df_18['cyl'].value_counts()
... 4.0     365
... 6.0     246
... 8.0     153

>>> df_18['cyl'] = df_18['cyl'].astype(int)
>>> df_18['cyl'].value_counts()
... 4     365
... 6     246
... 8     153

1
astype(int)zaten birkaç kez bahsedildi. Bu cevap yeni bir şey eklemiyor.
Georgy
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.