Как преобразовать этот список в фрейм данных? - PullRequest
1 голос
/ 07 ноября 2019

Я зацикливаюсь на веб-страницах, чтобы получить строки таблицы, а затем добавить каждую строку в фрейм данных. Тем не менее, я получаю список, который не может быть объединен в один фрейм данных. Как мне преобразовать этот список, чтобы разрешить pd.concat ()?

Я пробовал pd.DataFrame(data), но возвращает KeyError: 0

Вот результат печати (данных) https://imgur.com/a/t0v0QaU:

[          Unnamed: 0 2015-2016 2016-2017 2017-2018
0  Average net price    $6,497    $8,311    $7,035,           Unnamed: 0 2015-2016 2016-2017 2017-2018
0  Average net price   $26,916   $27,175   $27,584,           Unnamed: 0 2015-2016 2016-2017 2017-2018
0  Average net price    $8,123    $8,022    $7,687,           Unnamed: 0 2015-2016 2016-2017 2017-2018
0  Average net price         —   $16,694   $21,842,           Unnamed: 0 2015-2016 2016-2017 2017-2018
0  Average net price   $13,888   $12,989   $13,314,           Unnamed: 0 2015-2016 2016-2017 2017-2018
0  Average net price   $28,095   $27,925   $28,406,           Unnamed: 0 2015-2016 2016-2017 2017-2018
0  Average net price    $7,242    $6,960    $8,436,           Unnamed: 0 2015-2016 2016-2017 2017-2018
0  Average net price   $25,839   $26,930   $26,710,           Unnamed: 0 2015-2016 2016-2017 2017-2018
0  Average net price   $18,603   $16,450   $17,145]
import pandas as pd
import requests
from bs4 import BeautifulSoup as bs

data = []
url = 'https://nces.ed.gov/collegenavigator/?id='
ids = pd.read_excel('ids.xlsx')
for index, row in ids.iterrows():
    try:
        r = requests.get(url+str(row[0]))
        soup = bs(r.content, 'lxml')
        table = pd.read_html(str(soup.select_one('table:has(td:contains("Average net price"))')))
        data.append(table[0])
    except:
        pass
print(data)

Идентификаторы:

UnitID
180203
177834
222178
138558
412173
126182
188429
188438
168528
133872

В идеале, я хотел бы, чтобы выходные данные имели столбец идентификаторов и столбцы для каждого диапазона года (2015-2016, 2016-2017 и т. Д.) С чистыми ценами, заполненными в матрице, например: https://imgur.com/a/RC0hoGz

Ответы [ 3 ]

2 голосов
/ 07 ноября 2019

По сути, просто сохраните идентификатор в отдельном столбце проанализированных кадров данных. Теперь он игнорируется

...
for index, row in ids.iterrows(): 
    try: 
        r = requests.get(url+str(row[0])) 
        soup = bs(r.content, 'lxml') 
        table = pd.read_html(str(soup.select_one('table:has(td:contains("Average net price"))')), index_col=0)[0] 
        table['id'] = row[0] # save the Id in a separate column
        data.append(table.set_index('id'))
    except: 
        pass

df = pd.concat(data)

Результат:

       2015-2016 2016-2017 2017-2018
id                                  
180203    $6,497    $8,311    $7,035
222178   $26,916   $27,175   $27,584
138558    $8,123    $8,022    $7,687
412173         —   $16,694   $21,842
126182   $13,888   $12,989   $13,314
188429   $28,095   $27,925   $28,406
188438    $7,242    $6,960    $8,436
168528   $25,839   $26,930   $26,710
133872   $18,603   $16,450   $17,145
1 голос
/ 07 ноября 2019

Использование:

import pandas as pd
import requests
from bs4 import BeautifulSoup as bs

data = []
url = 'https://nces.ed.gov/collegenavigator/?id='
ids = pd.read_excel('ids.xlsx')

for index, row in ids.iterrows():

    try:
        r = requests.get(url+str(row[0]))
        soup = bs(r.content, 'lxml')
        table = pd.read_html(str(soup.select_one('table:has(td:contains("Average net price"))')))
        dataframe=table[0]
        dataframe.index=row
        data.append(dataframe)
    except:
        pass


df_values= (pd.concat(data,sort=False)
              .drop('Unnamed: 0',axis=1)
              .rename_axis(index='UnitID') )
print(df_values)

Вывод:

        2015-2016 2016-2017 2017-2018
UnitID                              
180203    $6,497    $8,311    $7,035
222178   $26,916   $27,175   $27,584
138558    $8,123    $8,022    $7,687
412173         —   $16,694   $21,842
126182   $13,888   $12,989   $13,314
188429   $28,095   $27,925   $28,406
188438    $7,242    $6,960    $8,436
168528   $25,839   $26,930   $26,710
133872   $18,603   $16,450   $17,145
1 голос
/ 07 ноября 2019

Интересный вопрос,

Так что, когда вы используете панды для чего-либо, обычно выдает серию или фрейм данных в качестве вывода. Поэтому, когда вы создали список с именем data, а затем добавили к нему table[0]. Вы думали, что добавляете список к нему (я думаю). Но pd.read_html дает данные. Так что вам просто нужно создать data как Dataframe, а затем добавить к нему каждый dataframe.

вот решение:

import pandas as pd
import requests
from bs4 import BeautifulSoup as bs

data = pd.DataFrame()
url = 'https://nces.ed.gov/collegenavigator/?id='
ids = pd.read_excel('ids.xlsx')
for index, row in ids.iterrows():
    try:
        r = requests.get(url+str(row[0]))
        soup = bs(r.content, 'lxml')
        table = pd.read_html(str(soup.select_one('table:has(td:contains("Average net price"))')))
        data = data.append(table[0], ignore_index=True)
    except:
        pass

Надеюсь, это поможет.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...