【问题标题】:How to write csv file from scraped data from web in python如何在 python 中从 Web 抓取的数据中写入 csv 文件
【发布时间】:2018-11-03 06:58:10
【问题描述】:

我正在尝试从网页上抓取数据并且也能够抓取。 使用以下脚本获取所有 div 类数据后,但我很困惑如何在 CSV 文件中写入数据。

名字列中的第一个数据 姓氏列中的姓氏数据 . .

from urllib.request import urlopen
from bs4 import BeautifulSoup

html = 'http://rerait.telangana.gov.in/PrintPreview/PrintPreview/UHJvamVjdElEPTQmRGl2aXNpb249MSZVc2VySUQ9MjAyODcmUm9sZUlEPTEmQXBwSUQ9NSZBY3Rpb249U0VBUkNIJkNoYXJhY3RlckQ9MjImRXh0QXBwSUQ9'

page = urlopen(html)

data = BeautifulSoup(page, 'html.parser')

name_box = data.findAll('div', attrs={'class': 'col-md-3 col-sm-3'}) #edited companyName_99a4824b -> companyName__99a4824b

for i in range(len(name_box)):
    data = name_box[i].text.strip()

数据:

Information Type
Individual

First Name
KACHAM
Middle Name

Last Name
RAJESHWAR
Father Full Name
RAMAIAH
Do you have any Past Experience ?
No
Do you have any registration in other State than registred State?
No
House Number
8-2-293/82/A/446/1
Building Name
SAI KRUPA
Street  Name
ROAD NO 20
Locality
JUBILEE HILLS
Landmark
JUBILEE HILLS
State
Telangana
Division
Division 1
District
Hyderabad
Mandal
Shaikpet
Village/City/Town

Pin Code
500033
Office Number
04040151614
Fax Number

Website URL

Authority Name

Plan Approval Number
1/18B/06558/2018
Project Name
SKV S ANANDA VILAS
Project Status
New Project
Proposed Date of Completion
17/04/2024
Litigations related to the project ?
No
Project Type
Residential
Are there any Promoter(Land Owner/ Investor) (as defined by Telangana RERA Order) in the project ?
Yes
Sy.No/TS No.
00
Plot No./House No.
10-2-327
Total Area(In sqmts)
526.74
Area affected in Road widening/FTL of Tanks/Nala Widening(In sqmts)
58.51
Net Area(In sqmts)
1
Total Building Units (as per approved plan)
1
Proposed Building Units(as per agreement)
1


Boundaries East
PLOT NO 213
Boundaries West
PLOT NO 215
Boundaries North
PLOT NO 199
Boundaries South
ROAD NO 8
Approved Built up Area (In Sqmts)
1313.55
Mortgage Area  (In Sqmts)
144.28
State
Telangana
District
Hyderabad
Mandal
Maredpally
Village/City/Town

Street
ROAD NO 8
Locality
SECUNDERABAD COURT
Pin Code
500026

上面是上面代码运行后得到的数据。

编辑

for i in range(len(name_box)):
    data = name_box[i].text.strip()
    print (data)
    fname = 'out.csv'
    with open(fname) as f:
        next(f)
        for line in f:
            head = []
            value = []
            for row in line:
                head.append(row)
            print (row)

预期

Information Type | First  | Middle Name | Last Name | ......
Individual       | KACHAM |             | RAJESHWAR | .....

我有 200 个 url,但所有 url 数据都不相同,这意味着其中一些缺失。如果数据不可用,我想这样写,然后写一个空白。

请提出建议。提前谢谢你

【问题讨论】:

  • 你考虑过使用 Pandas 吗?使用用于抓取网页内容pd.read_html() 和编写 CSV 文件df.to_csv() 的内置函数可以使您的代码更具可读性。
  • open(fname) 只是读取文件,而不是写入文件
  • 是的,这不是写作,因为在写作之前我想让数据像预期的结果一样。请帮忙
  • @Mark,不,熊猫会怎么做?如何在列名中写入行数据,如预期结果
  • 来自 pandas 模块:pandas.read_html() 会将 HTML 表格解析为 DataFrame。 df.to_csv() 会将 DataFrame 转换为 CSV。 pandas 模块文档非常好,可在pandas.pydata.org/pandas-docs/stable/generated/… 获得

标签: python python-3.x web-scraping beautifulsoup


【解决方案1】:

要写入 csv,您需要知道 head 和 body 中应该是什么值,在这种情况下,head 值应该是包含 <label 的 html 元素

from urllib2 import urlopen
from bs4 import BeautifulSoup

html = 'http://rerait.telangana.gov.in/PrintPreview/PrintPreview/UHJvamVjdElEPTQmRGl2aXNpb249MSZVc2VySUQ9MjAyODcmUm9sZUlEPTEmQXBwSUQ9NSZBY3Rpb249U0VBUkNIJkNoYXJhY3RlckQ9MjImRXh0QXBwSUQ9'

page = urlopen(html)

data = BeautifulSoup(page, 'html.parser')

name_box = data.findAll('div', attrs={'class': 'col-md-3 col-sm-3'}) #edited companyName_99a4824b -> companyName__99a4824b

heads = []
values = []

for i in range(len(name_box)):
    data = name_box[i].text.strip()
    dataHTML = str(name_box[i])
    if 'PInfoType' in dataHTML:
        # <div class="col-md-3 col-sm-3" id="PInfoType">
        # empty value, maybe additional data for "Information Type"
        continue

    if 'for="2"' in dataHTML:
        # <label for="2">No</label>
        # it should be head but actually value
        values.append(data)

    elif '<label' in dataHTML:
        # <label for="PersonalInfoModel_InfoTypeValue">Information Type</label>
        # head or top row
        heads.append(data)

    else:
        # <div class="col-md-3 col-sm-3">Individual</div>
        # value for second row
        values.append(data)

csvData = ', '.join(heads) + '\n' + ', '.join(values)    
with open("results.csv", 'w') as f:
    f.write(csvData)

print "finish."

【讨论】:

  • 谢谢,你能解释一下这些行吗:if 'PInfoType' in dataHTML: continue if 'for="2"' in dataHTML: values.append(data) elif '&lt;label' in dataHTML: heads.append(data)
  • 我正在尝试多个 url,但没有在第一个链接中将所有列都放在相同的位置。第二个链接:http://rerait.telangana.gov.in/PrintPreview/PrintPreview/UHJvamVjdElEPTE1NiZEaXZpc2lvbj0xJlVzZXJJRD0yMTA2NCZSb2xlSUQ9MSZBcHBJRD0yNDcmQWN0aW9uPVNFQVJDSCZDaGFyYWN0ZXJEPTQ3JkV4dEFwcElEPQ%3d%3d
  • 代码更新了解释。对于第二个链接,只需添加所需条件if... elif...
  • 谢谢,如何循环查看http://rerait.telangana.gov.in/PrintPreview/PrintPreview/UHJvamVjdElEPTE1NiZEaXZpc2lvbj0xJlVzZXJJRD0yMTA2NCZSb2xlSUQ9MSZBcHBJRD0yNDcmQWN0aW9uPVNFQVJDSCZDaGFyYWN0ZXJEPTQ3JkV4dEFwcElEPQ%3d%3d 这个链接?和Plot No. 46 &amp; 47, 2-2-647/8 &amp; 2-2-647/8/2 这个值我在两列中得到一个买想要的
  • 还建议在同一链接中使用表数据。我们可以在同一个csv中抓取吗?使用相同的代码
【解决方案2】:

问题:如何从抓取的数据中写入csv文件

Data 读入dict 并使用csv.DictWriter(... 写入CSV 文件。
关于: csv.DictWriter while next break Mapping Types — dict

  1. 跳过第一行,因为它是标题
  2. 循环Data
    1. key = next(data)
    2. value = next(data)
    3. 如果没有更多数据则中断循环
    4. 构建dict[key] = value
  3. 循环结束后,将dict写入CSV文件

输出

{'Individual': '', 'Father Full Name': 'RAMAIAH', 'First Name': 'KACHAM', 'Middle Name': '', 'Last Name': 'RAJESHWAR',... (omitted for brevity)

【讨论】:

  • 我已经尝试过,但没有得到预期的结果。可以分享一下代码吗?
  • @user10468005:编辑你的问题并展示你的努力,解释你卡在哪里。
猜你喜欢
  • 2017-02-10
  • 2017-05-21
  • 1970-01-01
  • 2018-09-30
  • 2020-02-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-10-05
相关资源
最近更新 更多