웹 페이지에서 Python 추출 테이블

Salman Mehmood 2023년6월21일
  1. 웹 페이지에서 Python 추출 테이블
  2. Pandas를 사용하여 웹 페이지에서 Python 추출 테이블
  3. lxml을 사용하여 웹 페이지에서 Python 추출 테이블
웹 페이지에서 Python 추출 테이블

이 기사의 주요 목적은 Pandas와 Python의 lxml을 사용하여 웹 페이지에서 테이블을 추출하는 방법을 보여주는 것입니다.

웹 페이지에서 Python 추출 테이블

데이터는 많은 정보가 매일 높은 빈도로 처리, 저장 및 추출되는 이 현대 시대에 매우 중요합니다. 이와 관련하여 우리 프로젝트는 특정 온라인 위치, 저장소 또는 웹 페이지에서 데이터를 추출하도록 요구할 수 있습니다.

이는 수많은 사용 사례에서 가능할 수 있습니다. 여러 가지 이유로 데이터를 추출, 처리 및 저장하거나 저장소에서 데이터를 추출하기 위해 공개 기록 보관 사이트에 액세스해야 할 수 있습니다.

이 작업을 수행하는 더 좋은 방법이 있지만 단순화를 위해 이것이 필수 방법이라고 가정합니다.

이 상황을 해결하려면 웹 페이지에 대한 연결을 설정하고, 페이지를 읽고, 테이블이 있는 경우 테이블을 찾고, 올바르게 추출하고, 적절한 형식으로 저장하는 솔루션을 고안해야 합니다. 이것은 우리 프로그램에서 처리될 수 있도록 하기 위한 것입니다.

이 문제에 대한 해결책은 여러 가지 방법으로 접근할 수 있으며 그 중 두 가지가 아래에 언급되어 있습니다.

Pandas를 사용하여 웹 페이지에서 Python 추출 테이블

계속 진행하기 전에 다음 모듈/패키지가 설치되어 있는지 확인하십시오.

  1. xml
  2. html5lib
  3. 아름다운수프4

다음 명령을 사용하여 pip로 언급된 패키지를 설치할 수 있습니다.

pip install lxml html5lib BeautifulSoup4

이는 다음과 같은 결과를 제공합니다.

Collecting lxml
  Downloading lxml-4.9.1-cp310-cp310-win_amd64.whl (3.6 MB)
     ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 3.6/3.6 MB 37.9 kB/s eta 0:00:00
Requirement already satisfied: html5lib in c:\program files\python310\lib\site-packages (1.1)
Collecting BeautifulSoup4
  Downloading beautifulsoup4-4.11.1-py3-none-any.whl (128 kB)
     ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 128.2/128.2 kB 29.0 kB/s eta 0:00:00
Requirement already satisfied: webencodings in c:\program files\python310\lib\site-packages (from html5lib) (0.5.1)
Requirement already satisfied: six>=1.9 in c:\program files\python310\lib\site-packages (from html5lib) (1.16.0)
Collecting soupsieve>1.2
  Downloading soupsieve-2.3.2.post1-py3-none-any.whl (37 kB)
Collecting requests
  Downloading requests-2.28.1-py3-none-any.whl (62 kB)
     ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 62.8/62.8 kB 420.8 kB/s eta 0:00:00
Collecting urllib3<1.27,>=1.21.1
  Downloading urllib3-1.26.12-py2.py3-none-any.whl (140 kB)
     ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 140.4/140.4 kB 1.0 MB/s eta 0:00:00
Collecting idna<4,>=2.5
  Downloading idna-3.4-py3-none-any.whl (61 kB)
     ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 61.5/61.5 kB 121.6 kB/s eta 0:00:00
Collecting charset-normalizer<3,>=2
  Downloading charset_normalizer-2.1.1-py3-none-any.whl (39 kB)
Collecting certifi>=2017.4.17
  Downloading certifi-2022.9.24-py3-none-any.whl (161 kB)
     ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 161.1/161.1 kB 1.4 MB/s eta 0:00:00
Installing collected packages: urllib3, idna, charset-normalizer, certifi, requests, soupsieve, lxml, BeautifulSoup4
Successfully installed BeautifulSoup4-4.11.1 lxml-4.9.1 soupsieve-2.3.2.post1 certifi-2022.9.24 charset-normalizer-2.1.1 idna-3.4 requests-2.28.1 urllib3-1.26.12

필요한 모듈을 설치한 후에는 구현 부분으로 넘어갈 차례입니다.

다음 코드를 고려하십시오.

import requests
import pandas as pd

url = "https://www.ffiec.gov/census/report.aspx?year=2020&county=009&state=09&report=demographic"

html = requests.get(url).content
df_list = pd.read_html(html)
df = df_list[-1]
print(df)

이는 다음과 같은 결과를 제공합니다.

    Tract Code Tract Income Level Distressed or Under-served Tract  ...  Minority Population Owner Occupied Units 1- to 4- Family Units
1       1202.0           Moderate                                No  ...                 3040                  918                  2010
2       1251.0             Middle                                No  ...                  551                 1400                  1555
3       1252.0           Moderate                                No  ...                 2088                 1139                  1992
4       1253.0           Moderate                                No  ...                 2443                  728                  1814
..         ...                ...                               ...  ...                  ...                  ...                   ...
95      1714.0           Moderate                                No  ...                 1278                  141                   638
96      1715.0           Moderate                                No  ...                 2241                  396                  1274
97      1716.0             Middle                                No  ...                 1466                 1378                  1803
98      1717.0             Middle                                No  ...                  820                 1456                  1647
99      1751.0             Middle                                No  ...                  851                  669                  1240

[100 rows x 12 columns]

Pandas 라이브러리를 사용하여 모든 웹 페이지에서 테이블을 쉽게 추출할 수 있습니다. Pandas 라이브러리의 read_html 메서드는 웹 페이지에서 데이터를 읽고 추출한 다음 데이터 프레임으로 변환하여 데이터가 Dataframe 객체가 되므로 원활한 데이터 처리를 지원하는 데 사용할 수 있습니다.

추출된 테이블은 Dataframe 개체를 CSV 파일로 저장하는 to_csv 메서드를 사용하여 CSV 파일로 저장할 수도 있습니다.

lxml을 사용하여 웹 페이지에서 Python 추출 테이블

다음 코드를 고려하십시오.

from lxml import etree
import urllib.request

site = "https://www.ffiec.gov/census/report.aspx?year=2020&county=009&state=09&report=demographic"

hdr = {
    "User-Agent": "Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.11 (KHTML, like Gecko) Chrome/23.0.1271.64 Safari/537.11",
    "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8",
    "Accept-Charset": "ISO-8859-1,utf-8;q=0.7,*;q=0.3",
    "Accept-Encoding": "none",
    "Accept-Language": "en-US,en;q=0.8",
    "Connection": "keep-alive",
}


request = urllib.request.Request(site, headers=hdr)
web = urllib.request.urlopen(request)
s = web.read()
html = etree.HTML(s)


# Get all 'tr'
tr_nodes = html.xpath('//table[@id="Report1_dgReportDemographic"]/tr')

# 'th' is inside first 'tr'
headers = [i.text for i in tr_nodes[0].xpath("th")]

# Get text from rest all 'tr'
td_content = [[td.text for td in tr.xpath("td")] for tr in tr_nodes[1:]]

for head in headers:
    print(head, end=" ")

print("")

for content in td_content:
    print(content)

이것은 아래와 같은 출력을 제공합니다:

Tract Code Tract Income Level  Distressed or Under   Tract Median Family Income % 2020 FFIEC Est. MSA/MD non-MSA/MD Median Family Income 2020 Est. Tract Median Family Income 2015 Tract Median Family Income Tract Population Tract Minority % Minority Population Owner Occupied Units 1- to 4- Family Units
['1201.00', 'Middle', 'No', '93.64', '$91,800', '$85,962', '$75,611', '6013', '26.44', '1590', '1862', '2248']
['1202.00', 'Moderate', 'No', '68.12', '$91,800', '$62,534', '$55,000', '6783', '44.82', '3040', '918', '2010']
['1251.00', 'Middle', 'No', '109.80', '$91,800', '$100,796', '$88,654', '4477', '12.31', '551', '1400', '1555']
['1252.00', 'Moderate', 'No', '62.55', '$91,800', '$57,421', '$50,506', '5912', '35.32', '2088', '1139', '1992']
['1253.00', 'Moderate', 'No', '57.28', '$91,800', '$52,583', '$46,250', '5164', '47.31', '2443', '728', '1814']
.
.
.
.
.

lxmlurllib를 사용하여 웹 페이지에서 테이블을 추출하고 처리할 수도 있습니다. 코드에서 알 수 있듯이 요청에 사용자 지정 헤더를 제공해야 합니다. 그렇지 않으면 403: Forbidden 오류가 수신됩니다.

요청이 성공하면 테이블 검색이 완료되고(특히 이 사이트에 대해) 테이블에서 헤더와 콘텐츠(행)를 수동으로 추출합니다.

이 옵션은 Pandas 모듈보다 약간 더 길고 복잡하지만 추출할 항목과 그렇지 않은 항목에 대해 더 많은 제어와 자유가 필요할 때 유용합니다.

Salman Mehmood avatar Salman Mehmood avatar

Hello! I am Salman Bin Mehmood(Baum), a software developer and I help organizations, address complex problems. My expertise lies within back-end, data science and machine learning. I am a lifelong learner, currently working on metaverse, and enrolled in a course building an AI application with python. I love solving problems and developing bug-free software for people. I write content related to python and hot Technologies.

LinkedIn