使用BeautifulSoup抓取iHerb网站商品价格遇到的问题求助
问题分析与代码修正
核心问题
- 列表重置导致仅保留单个商品价格:
main_list被定义在商品循环(for li in lis)内部,每次处理新商品时都会清空列表,最终仅能保留最后一个商品的价格。 - 冗余的价格循环:每个商品的
product-price-top容器下只有一个价格标签(折扣价或原价),不需要遍历prices列表,直接定位即可。
修正后的代码
def get_page_data(html): soup = BeautifulSoup(html, 'lxml') # 获取所有商品容器 product_containers = soup.find_all('div', class_="product-cell-container col-xs-12 col-sm-12 col-md-8 col-lg-6") # 把结果列表移到循环外,收集所有商品数据 all_products = [] for container in product_containers: product = {} # 获取商品名称 try: product['name'] = container.find('div', class_='absolute-link-wrapper').find('a').get('title') except: product['name'] = '' # 获取商品链接 try: product['url'] = container.find('div', class_='absolute-link-wrapper').find('a').get('href') except: product['url'] = '' # 获取商品价格 price_container = container.find('div', class_="product-price-top") try: # 优先获取折扣价 product['price'] = price_container.find("span", class_='price discount-green').text.strip() except AttributeError: # 没有折扣价则获取原价 try: product['price'] = price_container.find("span", class_='price').text.strip() except AttributeError: product['price'] = '' # 将当前商品数据加入总列表 all_products.append(product) # 打印所有商品数据 for item in all_products: print(f"商品名称: {item['name']}, 价格: {item['price']}, 链接: {item['url']}") return all_products
修改说明
- 将结果列表
all_products移至商品循环外部,确保所有商品数据都能被收集。 - 用字典存储单个商品的名称、链接、价格,结构更清晰,便于后续处理。
- 简化价格获取逻辑:每个商品仅需一次定位
product-price-top容器,先尝试抓取折扣价,失败后再抓取原价,避免不必要的循环。 - 增加了价格获取的双重异常捕获,防止部分商品无价格标签导致程序报错。
内容的提问来源于stack exchange,提问作者Danya
相关产品推荐
相关产品推荐

