# book ranking search
```python=
import requests
from bs4 import BeautifulSoup
import re
from datetime import date
import plotly.express as px
import pandas as pd
from functools import reduce
def convert_ranking_data(date_and_ranking):
date_origin = date.fromisoformat(date_and_ranking[0]["date"])
date_end = date.fromisoformat(date_and_ranking[-1]["date"])
print("date origin: %s" % date_origin)
print("date end: %s" % date_end)
total_days = ((date_end - date_origin).days + 1)
print("total days: %d" % total_days)
ranking_data = [None] * total_days
for dr in date_and_ranking:
date_current = date.fromisoformat(dr["date"])
index = (date_current - date_origin).days
print("index is %d. len is %d" % (index, len(ranking_data)))
ranking_data[index] = int(dr["ranking"])
return ranking_data
def get_ranking(link):
response = requests.get(link)
print(response.text)
soup = BeautifulSoup(response.text)
tags = soup.find_all("td", string=re.compile("文學新書暢銷榜"))
date_and_ranking = list(map(lambda x: {"date": x.find_previous_sibling().text, "ranking": x.find_next_sibling().text}, tags))
print(date_and_ranking)
date_and_ranking.reverse()
if len(date_and_ranking) == 0:
return []
return convert_ranking_data(date_and_ranking)
def fill_entries(arr, target):
arr.extend([None] * (target - len(arr)))
return arr
def draw_diagram(data):
df = pd.DataFrame(data)
fig = px.line(df)
fig.update_layout(yaxis = dict(autorange="reversed"))
fig.write_html('first_figure.html', auto_open=True)
def search():
site = "https://www.monster101.com"
url = site + "/s"
response = requests.post(url, data={"query": "張亦絢"})
print(response.text)
soup = BeautifulSoup(response.text)
link_tags = soup.select("td a")
result = list(map(lambda x: {"name": x.text, "link": site + x.get('href')}, link_tags))
data = {}
for r in result:
ranking_list = get_ranking(r["link"])
if len(ranking_list) > 0:
data[r["name"]] = ranking_list
entries = map(lambda x: len(x), data.values())
max_entries = reduce(lambda x, y: max(x, y), entries)
data = {k: fill_entries(v, max_entries) for k, v in data.items()}
print(data)
draw_diagram(data)
search()
```