2016-01-25 1 views
1

Я использую python 3.4. Я знаю, как использовать BeautifulSoup, чтобы очистить веб-страницу, но я пытаюсь найти наиболее эффективный способ выполнить это. Nexus factory image page (Android) содержит списки всех устройств Nexus и обновляется, когда доступна новая сборка. Новые сборки всегда добавляются к нижней части соответствующей таблицы. У меня есть список имен каждого устройства, как настоящее имя, так и кодовое имя, и я просто извлекаю их (сами устройства обновляются только раз в год, если это, и только некоторые из устройств по-прежнему получают обновления).Скребок для нижней строки таблицы

Что было бы самым эффективным способом вытащить нижний вход из каждой таблицы? Я планирую сохранять каждую строку с первых <td> в нижних строках в виде маринованных объектов, поэтому я могу легко сравнить строки позже, чтобы проверить, является ли текущая нижняя строка новой, но я не уверен, что лучший способ - очистить самой записи.

Каждый <tr> имеет идентификатор формата devnamebuildnumber. Поскольку у меня есть имя каждого устройства и у вас будет последняя строка, я должен иметь возможность искать с помощью soup.find("tr", id=dev + buildstring). Тем не менее, это возвращает каждого брата и ребенка найденной строки, поэтому я не уверен, как наилучшим образом использовать это.

ответ

2

Вот что вам поможет. Идея состоит в том, чтобы получить элементы h2 с атрибутом id - кроме самого первого элемента это будут элементы имени устройства. Для каждого найденного элемента давайте добавим следующий элемент table и проанализируем версии в списке. Реализация:

from pprint import pprint 

import requests 
from bs4 import BeautifulSoup 


url = "https://developers.google.com/android/nexus/images" 
response = requests.get(url) 

soup = BeautifulSoup(response.content, "lxml") 

data = {} 
for device in soup.find_all("h2", id=True)[1:]: 
    device_name = device.get_text(strip=True) 

    data[device_name] = [version.find("td").get_text(strip=True) 
         for version in device.find_next("table").find_all("tr", id=True)] 

pprint(data) 

Печатает словарь с именами устройств в качестве ключей и версий в качестве значений:

{'"angler" for Nexus 6P': ['6.0.0 (MDA89D)', 
          '6.0.0 (MDB08K)', 
          '6.0.0 (MDB08L)', 
          '6.0.0 (MDB08M)', 
          '6.0.0 (MMB29N)', 
          '6.0.1 (MMB29M)', 
          '6.0.1 (MMB29P)'], 
'"bullhead" for Nexus 5X': ['6.0.0 (MDA89E)', 
          '6.0.0 (MDB08I)', 
          '6.0.0 (MDB08L)', 
          '6.0.0 (MDB08M)', 
          '6.0.1 (MMB29K)', 
          '6.0.1 (MMB29P)'], 
'"fugu" for Nexus Player': ['5.0 (LRX21M)', 
          '5.0 (LRX21V)', 
          '5.1.0 (LMY47D)', 
          '5.1.1 (LMY47V)', 
          '5.1.1 (LMY48J)', 
          '5.1.1 (LMY48N)', 
          '6.0.0 (MRA58K)', 
          '6.0.0 (MRA58N)', 
          '6.0.1 (MMB29M)', 
          '6.0.1 (MMB29T)'], 
'"hammerhead" for Nexus 5 (GSM/LTE)': ['4.4 (KRT16M)', 
             '4.4.2 (KOT49H)', 
             '4.4.3 (KTU84M)', 
             '4.4.4 (KTU84P)', 
             '4.4.4 Release 2 (For 2Degrees/NZ, ' 
             'Telstra/AUS and India ONLY) (KTU84Q)', 
             '5.0 (LRX21O)', 
             '5.0.1 (LRX22C)', 
             '5.1.0 (LMY47D)', 
             '5.1.0 (LMY47I)', 
             '5.1.1 (LMY48B)', 
             '5.1.1 (LMY48I)', 
             '5.1.1 (LMY48M)', 
             '6.0.0 (MRA58K)', 
             '6.0.0 (MRA58N)', 
             '6.0.1 (MMB29K)', 
             '6.0.1 (MMB29S)'], 
'"mantaray" for Nexus 10': ['4.2.2 (JDQ39)', 
          '4.3 (JWR66Y)', 
          '4.4 (KRT16S)', 
          '4.4.2 (KOT49H)', 
          '4.4.3 (KTU84L)', 
          '4.4.4 (KTU84P)', 
          '5.0 (LRX21P)', 
          '5.0.1 (LRX22C)', 
          '5.0.2 (LRX22G)', 
          '5.1.0 (LMY47D)', 
          '5.1.1 (LMY47V)', 
          '5.1.1 (LMY48I)', 
          '5.1.1 (LMY48M)', 
          '5.1.1 (LMY48T)', 
          '5.1.1 (LMY48X)', 
          '5.1.1 (LMY48Z)', 
          '5.1.1 (LMY49F)'], 
'"mysid" for Galaxy Nexus "toro" (Verizon CDMA/LTE)': ['4.0.4 (IMM76K)', 
                 '4.1.1 (JRO03O)', 
                 '4.2.2 (JDQ39)'], 
'"mysidspr" for Galaxy Nexus "toroplus" (Sprint CDMA/LTE)': ['4.1.1 (FH05)', 
                   '4.2.1 (GA02)'], 
'"nakasi" for Nexus 7 (Wi-Fi)': ['4.1.2 (JZO54K)', 
            '4.2.2 (JDQ39)', 
            '4.3 (JWR66Y)', 
            '4.4 (KRT16S)', 
            '4.4.2 (KOT49H)', 
            '4.4.3 (KTU84L)', 
            '4.4.4 (KTU84P)', 
            '5.0 (LRX21P)', 
            '5.0.2 (LRX22G)', 
            '5.1.0 (LMY47D)', 
            '5.1.1 (LMY47V)'], 
'"nakasig" for Nexus 7 (Mobile)': ['4.2.2 (JDQ39)', 
            '4.3 (JWR66Y)', 
            '4.4 (KRT16S)', 
            '4.4.2 (KOT49H)', 
            '4.4.3 (KTU84L)', 
            '4.4.4 (KTU84P)', 
            '5.0.2 (LRX22G)', 
            '5.1.0 (LMY47D)', 
            '5.1.1 (LMY47V)'], 
'"occam" for Nexus 4': ['4.2.2 (JDQ39)', 
         '4.3 (JWR66Y)', 
         '4.4 (KRT16S)', 
         '4.4.2 (KOT49H)', 
         '4.4.3 (KTU84L)', 
         '4.4.4 (KTU84P)', 
         '5.0 (LRX21T)', 
         '5.0.1 (LRX22C)', 
         '5.1.0 (LMY47O)', 
         '5.1.1 (LMY47V)', 
         '5.1.1 (LMY48I)', 
         '5.1.1 (LMY48M)', 
         '5.1.1 (LMY48T)'], 
'"razor" for Nexus 7 [2013] (Wi-Fi)': ['4.3 (JSS15Q)', 
             '4.3 (JSS15R)', 
             '4.4 (KRT16S)', 
             '4.4.2 (KOT49H)', 
             '4.4.3 (KTU84L)', 
             '4.4.4 (KTU84P)', 
             '5.0 (LRX21P)', 
             '5.0.1 (LRX22C)', 
             '5.0.2 (LRX22G)', 
             '5.1.0 (LMY47O)', 
             '5.1.1 (LMY47V)', 
             '5.1.1 (LMY48G)', 
             '5.1.1 (LMY48I)', 
             '5.1.1 (LMY48M)', 
             '5.1.1 (LMY48T)', 
             '6.0.0 (MRA58K)', 
             '6.0.0 (MRA58U)', 
             '6.0.0 (MRA58V)', 
             '6.0.1 (MMB29K)', 
             '6.0.1 (MMB29O)'], 
'"razorg" for Nexus 7 [2013] (Mobile)': ['4.3 (JLS36C)', 
              '4.3.1 (JLS36I)', 
              '4.4 (KRT16S)', 
              '4.4.2 (KOT49H)', 
              '4.4.2_r2 (Verizon) (KVT49L)', 
              '4.4.3 (KTU84L)', 
              '4.4.4 (KTU84P)', 
              '5.0.2 (LRX22G)', 
              '5.1.0 (LMY47O)', 
              '5.1.1 (LMY47V)', 
              '5.1.1 (LMY48P)', 
              '5.1.1 (LMY48U)', 
              '5.1.1 (LMY48X)', 
              '5.1.1 (LMY48Z)', 
              '6.0.0 (MRA58K)', 
              '6.0.0 (MRA58N)', 
              '6.0.0 (MRA58V)', 
              '6.0.0 (MRA59B)', 
              '6.0.1 (MMB29K)', 
              '6.0.1 (MMB29O)'], 
'"ryu" for Pixel C': ['6.0.1 (MXB48J)', '6.0.1 (MXB48K)'], 
'"shamu" for Nexus 6': ['5.0 (LRX21O)', 
         '5.0.1 (LRX22C)', 
         '5.1.0 (LMY47D)', 
         '5.1.0 (LMY47E)', 
         '5.1.0 (LMY47I)', 
         '5.1.0 (For T-Mobile ONLY) (LMY47M)', 
         '5.1.1 (All carriers except T-Mobile US) (LMY47Z)', 
         '5.1.1 (For T-Mobile ONLY) (LYZ28E)', 
         '5.1.1 (For Project Fi ONLY) (LVY48C)', 
         '5.1.1 (LMY48I)', 
         '5.1.1 (For T-Mobile ONLY) (LYZ28J)', 
         '5.1.1 (For Project Fi ONLY) (LVY48E)', 
         '5.1.1 (LMY48M)', 
         '5.1.1 (For T-Mobile ONLY) (LYZ28K)', 
         '5.1.1 (For Project Fi ONLY) (LVY48F)', 
         '5.1.1 (LMY48T)', 
         '5.1.1 (For T-Mobile ONLY) (LYZ28M)', 
         '5.1.1 (For Project Fi ONLY) (LVY48H)', 
         '5.1.1 (LMY48W)', 
         '5.1.1 (LMY48X)', 
         '5.1.1 (LMY48Y)', 
         '5.1.1 (For T-Mobile ONLY) (LYZ28N)', 
         '5.1.1 (For Project Fi ONLY) (LVY48I)', 
         '6.0.0 (MRA58K)', 
         '6.0.0 (MRA58N)', 
         '6.0.0 (MRA58R)', 
         '6.0.0 (MRA58X)', 
         '6.0.1 (MMB29K)', 
         '6.0.1 (MMB29S)'], 
'"soju" for Nexus S (worldwide version, i9020t and i9023)': ['2.3.6 (GRK39F)', 
                   '4.0.4 (IMM76D)', 
                   '4.1.2 (JZO54K)'], 
'"sojua" for Nexus S (850MHz version, i9020a)': ['2.3.6 (GRK39F)', 
                '4.0.4 (IMM76D)', 
                '4.1.2 (JZO54K)'], 
'"sojuk" for Nexus S (Korea version, m200)': ['2.3.6 (GRK39F)', 
               '4.0.4 (IMM76D)', 
               '4.1.1 (JRO03E)'], 
'"sojus" for Nexus S 4G (d720)': ['2.3.7 (GWK74)', 
            '4.0.4 (IMM76D)', 
            '4.1.1 (JRO03R)'], 
'"takju" for Galaxy Nexus "maguro" (GSM/HSPA+) (with Google Wallet)': ['4.0.4 ' 
                     '(IMM76I)', 
                     '4.1.2 ' 
                     '(JZO54K)', 
                     '4.2.2 ' 
                     '(JDQ39)', 
                     '4.3 ' 
                     '(JWR66Y)'], 
'"tungsten" for Nexus Q': ['4.0.4 (IAN67K)'], 
'"volantis" for Nexus 9 (Wi-Fi)': ['5.0 (LRX21Q)', 
            '5.0 (LRX21R)', 
            '5.0.1 (LRX22C)', 
            '5.0.2 (LRX22L)', 
            '5.1.1 (LMY47X)', 
            '5.1.1 (LMY48I)', 
            '5.1.1 (LMY48M)', 
            '5.1.1 (LMY48T)', 
            '6.0.0 (MRA58K)', 
            '6.0.0 (MRA58N)', 
            '6.0.1 (MMB29K)', 
            '6.0.1 (MMB29S)'], 
'"volantisg" for Nexus 9 (LTE)': ['5.0.1 (LRX22C)', 
            '5.0.2 (LRX22L)', 
            '5.1.1 (LMY47X)', 
            '5.1.1 (LMY48I)', 
            '5.1.1 (LMY48M)', 
            '5.1.1 (LMY48T)', 
            '5.1.1 (LMY48X)', 
            '5.1.1 (LMY48Z)', 
            '5.1.1 (LMY49F)', 
            '6.0.0 (MRA58K)', 
            '6.0.0 (MRA58N)', 
            '6.0.1 (MMB29K)', 
            '6.0.1 (MMB29S)'], 
'"yakju" for Galaxy Nexus "maguro" (GSM/HSPA+)': ['4.0.4 (IMM76I)', 
                '4.1.2 (JZO54K)', 
                '4.2.2 (JDQ39)', 
                '4.3 (JWR66Y)']} 
+0

Это то, что я пошел с, хотя Я немного изменил его для моего кода. Спасибо! – vaindil

1

Следующая создает список, содержащий последнюю запись от каждого устройства. Для этого вам все еще нужно перебрать все элементы, а потом просто держать последнюю запись следующим образом:

from bs4 import BeautifulSoup  
import requests 


html = requests.get("https://developers.google.com/android/nexus/images") 
soup = BeautifulSoup(html.text, "lxml") 
models = [] 

for h2 in soup.find_all('h2', id=True)[1:]: 
    tr = h2.find_next('table').find_all('tr', id=True)[-1] 
    td = [t.text.strip() for t in tr.find_all('td')] 
    models.append([h2.text] + td) 

for device, version, link, cs1, cs2 in models: 
    print '{}, {}'.format(device, version) 

Это будет выглядеть следующим образом:

"ryu" for Pixel C, 6.0.1 (MXB48K) 
"angler" for Nexus 6P, 6.0.1 (MMB29P) 
"bullhead" for Nexus 5X, 6.0.1 (MMB29P) 
"shamu" for Nexus 6, 6.0.1 (MMB29S) 
"fugu" for Nexus Player, 6.0.1 (MMB29T) 
"volantisg" for Nexus 9 (LTE), 6.0.1 (MMB29S) 
"volantis" for Nexus 9 (Wi-Fi), 6.0.1 (MMB29S) 
"hammerhead" for Nexus 5 (GSM/LTE), 6.0.1 (MMB29S) 
"razor" for Nexus 7 [2013] (Wi-Fi), 6.0.1 (MMB29O) 
"razorg" for Nexus 7 [2013] (Mobile), 6.0.1 (MMB29O) 
"mantaray" for Nexus 10, 5.1.1 (LMY49F) 
"occam" for Nexus 4, 5.1.1 (LMY48T) 
"nakasi" for Nexus 7 (Wi-Fi), 5.1.1 (LMY47V) 
"nakasig" for Nexus 7 (Mobile), 5.1.1 (LMY47V) 
"tungsten" for Nexus Q, 4.0.4 (IAN67K) 
"takju" for Galaxy Nexus "maguro" (GSM/HSPA+) (with Google Wallet), 4.3 (JWR66Y) 
"yakju" for Galaxy Nexus "maguro" (GSM/HSPA+), 4.3 (JWR66Y) 
"mysid" for Galaxy Nexus "toro" (Verizon CDMA/LTE), 4.2.2 (JDQ39) 
"mysidspr" for Galaxy Nexus "toroplus" (Sprint CDMA/LTE), 4.2.1 (GA02) 
"soju" for Nexus S (worldwide version, i9020t and i9023), 4.1.2 (JZO54K) 
"sojua" for Nexus S (850MHz version, i9020a), 4.1.2 (JZO54K) 
"sojuk" for Nexus S (Korea version, m200), 4.1.1 (JRO03E) 
"sojus" for Nexus S 4G (d720), 4.1.1 (JRO03R) 
Смежные вопросы