Korzystam z Python 3.2.1 i nie mogę zaimportować StringIO
modułu. Używam
io.StringIO
i działa, ale nie można go używać z numpy
„s genfromtxt
jak to:
x="1 3\n 4.5 8"
numpy.genfromtxt(io.StringIO(x))
Otrzymuję następujący błąd:
TypeError: Can't convert 'bytes' object to str implicitly
a kiedy piszę import StringIO
, mówi
ImportError: No module named 'StringIO'
źródło
TypeError
s (oczekiwany argument łańcuchowy, dostał „bajty”), jeśli dokonasz tej zmiany w izolacji. Musisz dokładnie odróżnić btyes i str (Unicode) w Pythonie 3.from io import StringIO
StringIO
ifrom io import BytesIO
należy go zastosować. Testowałem się na Pythonie 3.5 @ eclipse pyDev + win7 x64. Daj mi znać, jeśli się mylę, dzięki.W moim przypadku użyłem:
źródło
W Pythonie 3
numpy.genfromtxt
oczekuje strumienia bajtów. Użyj następujących opcji:źródło
Dziękuję OP za pytanie i Roman za odpowiedź. Musiałem trochę poszukać, żeby to znaleźć; Mam nadzieję, że poniższe informacje pomagają innym.
Python 2.7
Zobacz: https://docs.scipy.org/doc/numpy/user/basics.io.genfromtxt.html
Python 3.5:
Na bok:
dtype = "| Sx", gdzie x = dowolny z {1, 2, 3, ...}:
dtypy. Różnica między S1 i S2 w Pythonie
„Ciągi | S1 i | S2 są deskryptorami typu danych; pierwszy oznacza, że tablica przechowuje ciągi o długości 1, drugi o długości 2. ...”
źródło
Możesz użyć StringIO z sześciu modułów:
źródło
Kod Romana Shapovalova powinien działać w Pythonie 3.x, a także w Pythonie 2.6 / 2.7. Oto znowu z pełnym przykładem:
Wynik:
Wyjaśnienie dotyczące Python 3.x:
numpy.genfromtxt
pobiera strumień bajtów (obiekt podobny do pliku interpretowany jako bajty zamiast Unicode).io.BytesIO
pobiera ciąg bajtów i zwraca strumień bajtów.io.StringIO
, z drugiej strony, wziąłby ciąg Unicode i zwrócił strumień Unicode.x
zostaje przypisany ciąg literału, który w Pythonie 3.x jest ciągiem Unicode.encode()
pobiera ciąg Unicodex
i tworzy z niego ciąg bajtów, co dajeio.BytesIO
poprawny argument.Jedyną różnicą w Pythonie 2.6 / 2.7 jest to, że
x
jest to ciąg bajtów (zakładając, żefrom __future__ import unicode_literals
nie jest używany), a następnieencode()
pobiera ciąg bajtówx
i nadal tworzy z niego ten sam ciąg bajtów. Wynik jest taki sam.Ponieważ jest to jedno z najbardziej popularnych pytań dotyczących SO
StringIO
, oto kilka wyjaśnień dotyczących instrukcji importu i różnych wersji Pythona.Oto klasy, które pobierają ciąg i zwracają strumień:
io.BytesIO
(Python 2.6, 2.7 i 3.x) - Pobiera ciąg bajtów. Zwraca strumień bajtów.io.StringIO
(Python 2.6, 2.7 i 3.x) - Pobiera ciąg znaków Unicode. Zwraca strumień Unicode.StringIO.StringIO
(Python 2.x) - Pobiera ciąg bajtów lub ciąg Unicode. Jeśli ciąg bajtów, zwraca strumień bajtów. Jeśli ciąg znaków Unicode, zwraca strumień Unicode.cStringIO.StringIO
(Python 2.x) - Szybsza wersjaStringIO.StringIO
ciągów Unicode, które nie zawierają znaków ASCII, ale nie mogą z nich korzystać.Uwaga:
StringIO.StringIO
jest importowany jakofrom StringIO import StringIO
, a następnie używany jakoStringIO(...)
. Albo to, albo zrobiszimport StringIO
i użyjeszStringIO.StringIO(...)
. Nazwa modułu i nazwa klasy są po prostu takie same. Jest podobny dodatetime
tego.Czego używać, w zależności od obsługiwanych wersji Python:
Jeśli obsługujesz tylko Python 3.x: Po prostu użyj
io.BytesIO
lub wio.StringIO
zależności od rodzaju danych, z którymi pracujesz.Jeśli obsługujesz zarówno Python 2.6 / 2.7, jak i 3.x lub próbujesz zmienić kod z 2.6 / 2.7 na 3.x: Najłatwiejszą opcją jest nadal użycie
io.BytesIO
lubio.StringIO
. ChociażStringIO.StringIO
jest elastyczny i dlatego wydaje się preferowany w wersji 2.6 / 2.7, ta elastyczność może maskować błędy, które pojawią się w wersji 3.x. Na przykład miałem kod, który używałStringIO.StringIO
lubio.StringIO
zależał od wersji Pythona, ale tak naprawdę przekazałem ciąg bajtów, więc kiedy przystąpiłem do testowania go w Pythonie 3.x, nie udało się i musiałem go naprawić.Kolejną zaletą korzystania
io.StringIO
jest obsługa uniwersalnych nowych linii. Jeśli zdasz argument słowa kluczowegonewline=''
wio.StringIO
, to będzie w stanie podzielić linie na dowolnym\n
,\r\n
lub\r
. Odkryłem,StringIO.StringIO
że potknie się\r
w szczególności.Zauważ, że jeśli importujesz
BytesIO
lubStringIO
zsix
, dostajesz sięStringIO.StringIO
do Python 2.x i odpowiedniej klasy zio
Python 3.x. Jeśli zgadzasz się z oceną z moich poprzednich akapitów, to w rzeczywistości jest to jeden przypadek, w którym powinieneś unikaćsix
i po prostu importować zio
niego.Jeśli obsługujesz Python w wersji 2.5 lub nowszej i 3.x: Będziesz potrzebował wersji
StringIO.StringIO
2.5 lub nowszej, więc równie dobrze możesz użyćsix
. Ale zdaj sobie sprawę, że generalnie bardzo trudno jest obsługiwać zarówno wersje 2.5, jak i 3.x, więc powinieneś rozważyć obniżenie wersji najniższej obsługiwanej wersji do wersji 2.6, jeśli to w ogóle możliwe.źródło
Aby przykłady z tego miejsca działały w Pythonie 3.5.2, możesz przepisać w następujący sposób:
Przyczyną zmiany może być to, że zawartość pliku znajduje się w danych (bajtach), które nie tworzą tekstu, dopóki nie zostaną w jakiś sposób zdekodowane.
genfrombytes
może być lepsza nazwa niżgenfromtxt
.źródło
Spróbuj tego
z StringIO importuj StringIO
x = „1 3 \ n 4,5 8”
numpy.genfromtxt (StringIO (x))
źródło