TypeError: требуется байтоподобный объект, а не 'str' в python и CSV


173

TypeError: требуется байтоподобный объект, а не 'str'

Ошибка выше при выполнении кода ниже python для сохранения данных таблицы HTML в файле CSV. не знаю, как получить rideup.pls, помогите мне.

import csv
import requests
from bs4 import BeautifulSoup

url='http://www.mapsofindia.com/districts-india/'
response=requests.get(url)
html=response.content

soup=BeautifulSoup(html,'html.parser')
table=soup.find('table', attrs={'class':'tableizer-table'})
list_of_rows=[]
for row in table.findAll('tr')[1:]:
    list_of_cells=[]
    for cell in row.findAll('td'):
        list_of_cells.append(cell.text)
    list_of_rows.append(list_of_cells)
outfile=open('./immates.csv','wb')
writer=csv.writer(outfile)
writer.writerow(["SNo", "States", "Dist", "Population"])
writer.writerows(list_of_rows)

выше последней строки.



привет - я пытался запустить это на своем ATOM в MX-Linux - но я получаю следующее: «Обратный вызов (последний вызов был последним): файл" /home/martin/.atom/python/examples/bs_gumtree_pl.py ", строка 20, в <module> writer.writerows (list_of_rows) UnicodeEncodeError: кодек 'ascii' не может кодировать символ u '\ xa0' в позиции 0: порядковый номер не находится в диапазоне (128) [Закончено в 2.015s] ´ хорошо, интересно, что продолжается здесь!? люблю слышать от вас
ноль

Ответы:


332

Вы используете методологию Python 2 вместо Python 3.

Изменить:

outfile=open('./immates.csv','wb')

Для того, чтобы:

outfile=open('./immates.csv','w')

и вы получите файл со следующим выводом:

SNo,States,Dist,Population
1,Andhra Pradesh,13,49378776
2,Arunachal Pradesh,16,1382611
3,Assam,27,31169272
4,Bihar,38,103804637
5,Chhattisgarh,19,25540196
6,Goa,2,1457723
7,Gujarat,26,60383628
.....

В Python 3 CSV принимает ввод в текстовом режиме, тогда как в Python 2 он принимает его в двоичном режиме.

Отредактировано для добавления

Вот код, который я запустил:

url='http://www.mapsofindia.com/districts-india/'
html = urllib.request.urlopen(url).read()
soup = BeautifulSoup(html)
table=soup.find('table', attrs={'class':'tableizer-table'})
list_of_rows=[]
for row in table.findAll('tr')[1:]:
    list_of_cells=[]
    for cell in row.findAll('td'):
        list_of_cells.append(cell.text)
    list_of_rows.append(list_of_cells)
outfile = open('./immates.csv','w')
writer=csv.writer(outfile)
writer.writerow(['SNo', 'States', 'Dist', 'Population'])
writer.writerows(list_of_rows)

21
Для использования с csvмодулем Python 3 openтакже должен иметь newline=''в качестве параметра [ref ]
Марк Толонен

1
Измените строку 'wb' на 'w'. Большое спасибо
Loc Huynh

Если вы используете буфер, посмотрите ответ Винилла !
Handras

привет - я попробовал код - и получил следующее: `Traceback (последний вызов был последним): файл" /home/martin/.atom/python/examples/bs_gumtree_pl.py ", строка 20, в <module> UnicodeEncodeError : кодек «ascii» не может кодировать символ u '\ xa0' в позиции 0: порядковый номер не находится в диапазоне (128) [Закончено за 1.415 с] `у меня нет клея, что происходит здесь
ноль

21

У меня была такая же проблема с Python3. Мой код писал в io.BytesIO().

Замена на io.StringIO()решена.


со мной случается и с
stringio

Одно соображение: io.StringIO()жадность памяти и может быть головной болью с большими файлами.
Флавио

1
file = open('parsed_data.txt', 'w')
for link in soup.findAll('a', attrs={'href': re.compile("^http")}): print (link)
soup_link = str(link)
print (soup_link)
file.write(soup_link)
file.flush()
file.close()

В моем случае я использовал BeautifulSoup для написания .txt с Python 3.x. У него была та же проблема. Как сказал @tsduteba, замените 'wb' в первой строке на 'w'.


Когда вы даете ответ, желательно дать какое-то объяснение, ПОЧЕМУ ваш ответ тот. В этом случае чем этот ответ отличается от принятого ответа?
Стивен Раух

@StephenRauch Спасибо за ваши комментарии. Я новичок здесь и только начал изучать Python несколько недель назад. Я постараюсь дать лучший ответ в будущем.
Ян Ли

Вы можете отредактировать этот пост и добавить больше деталей. Нажмите кнопку редактирования ниже и слева от поста.
Стивен Раух

@StephenRauch Спасибо за ваши советы!
Ян Ли


1

Вы открываете файл CSV в двоичном режиме, он должен быть 'w'

import csv

# open csv file in write mode with utf-8 encoding
with open('output.csv','w',encoding='utf-8',newline='')as w:
    fieldnames = ["SNo", "States", "Dist", "Population"]
    writer = csv.DictWriter(w, fieldnames=fieldnames)
    # write list of dicts
    writer.writerows(list_of_dicts) #writerow(dict) if write one row at time
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.