#課題
Colaboratoryで、データを集めやすい市場・競馬等のデータを収集して、参考になるコードを試しながら、Pythonの勉強をしています。
現在、データの処理結果を、データフレームの新しい列に追加する処理で苦戦しています。
色々試しましたが、自身の力が不足しており、どうしても解決できませんでした。
恐れ入りますが、初学者なこともあり、どのようなコードを、どこに入れればよいのか、ご教示いただきたくお願い申し上げる次第です。
#実現したいこと
①縦向きに出力されるのデータの処理結果(deffの値)を、②別途作成しているデータフレームの背番号(no)に応じて、データフレームの新しい列に横向きに、for文で回しながら追加したい。という内容です。
色々試しましたが、自身の力が不足しており、どうしても解決できませんでした。
恐れ入りますが、初学者なこともあり、どのようなコードを、どこに入れればよいのか、ご教示いただきたくお願い申し上げる次第です。
前提
**#1.データ処理結果
データの処理結果は下表のように、縦向きに、出力されます。
データ処理のコードは下記のソースコード及び参考URLをご参照ください。
ソースコード①
ソースコードは、https://zenn.dev/moripon/articles/ed5caa9c1d621e
(出所:pyparsingで競馬のコーナー通過順位をパースより引用)
import numpy as np
import pandas as pd
import pyparsing as pp
columns = ['diff', 'horse_no']
DIFF_GROUP = 0.3
DIFF_MIN = 1.5
DIFF_MID = 3.0
DIFF_MUCH = 6.0
class ParsePass():
def __init__(self): horse_no = pp.Word(pp.nums).setParseAction(self._horse_no_action) group = pp.Suppress(pp.Literal('(')) + \ pp.Optional(pp.delimitedList(pp.Word(pp.nums), delim=',')) + \ pp.Suppress(pp.Literal(')')) group.ignore('*') group.setParseAction(self._group_action) element = (group | horse_no) diff_min = pp.Suppress(pp.Optional(pp.Literal(','))).setParseAction(self._diff_min_action) + element diff_mid = pp.Suppress(pp.Literal('-')).setParseAction(self._diff_mid_action) + element diff_much = pp.Suppress(pp.Literal('=')).setParseAction(self._diff_much_action) + element self._passing_order = element + pp.ZeroOrMore( diff_mid | diff_much | diff_min ) def _horse_no_action(self, token): self._data = self._data.append({'diff':self._diff, 'horse_no':token[0]}, ignore_index=True) return def _group_action(self, token): for no in token: self._data = self._data.append({'diff':self._diff, 'horse_no':no}, ignore_index=True) self._diff += DIFF_GROUP self._diff -= DIFF_GROUP return def _diff_min_action(self, token): self._diff += DIFF_MIN return def _diff_mid_action(self, token): self._diff += DIFF_MID return def _diff_much_action(self, token): self._diff += DIFF_MUCH return def parse(self, pass_str): # 初期化 self._data = pd.DataFrame(columns=columns) self._diff = 0 # parse self._passing_order.parseString(pass_str) # index調整 self._data.index = np.arange(1, len(self._data)+1) self._data.index.name = 'rank' return self._data
test data
下は算出結果の出力例です。実際はfor文で回すため、該当のソースコード②を先に実行してから、pass_data =results[1]として出力しています。
if name == 'main':
pass_data = ["(*6,10)11(4,2,9)-(1,5)12,8,14(3,13,15)7-16",
"6(10,11)(4,2,9)(1,5)12(8,14)(3,13,15)7=16",
"12(7,14)8(6,11)9(3,5)(2,10)(1,4,13)",
"12(7,14)8(6,11)9(2,5)(3,1,10)(4,13)",
" (*10,14)-(8,4)-(12,11,9)5(2,1)7,6,13=3",
"(10,*14)-(8,4)-(11,1)2,9,5,6-(7,13)-12-3"]
pass_parsing = ParsePass()
pass_str in pass_data:
print(pass_parsing.parse(pass_str))
実現したいこと
現在、競技ID、最終順位、背番号、各通過地点のrankをpandasのデータフレーム(以下、現データフレーム)に格納しています。
実現したいことは、下表上段(黄色)の現データフレームの背番号(no)毎に、上述#1のデータ処理結果のnoに合致するdeffの数値(表の真中の列の数値)を抽出して、競技IDをKeyとしてfor文で回しながら、現データフレームの新しい列に横向きにdeffの数値を加えていきたいです(下図の緑色箇所)
できたこと、できないこと
<できたこと>
競技IDをKeyとして、for文を回しながら、各地点の通過順位(rank)を取得すること、競技IDをKeyとして、for文を回しながら、#1の処理結果を出力することはできました。
<できないこと>
出力結果から①deffの数値が取り出せないこと、②現データフレームの競技ID、背番号(no)に応じて、deffの数値を現データフレームの新しい列に追加するためのfor文が書けませんでした。
なお、競技IDをKeyとしてfor文で回すために以下のコードを利用しています。
本ソースコードを先に実行してから、上述のソースコード①のtest dataにおいて、pass_data =results[1]として出力する。このコードの最後のresultsにあたります。
どうぞよろしくお願いいたします。
ソースコード②
import pandas as pd import time from tqdm import tqdm def scrape_race_results(race_id_list, pre_race_results={}): race_results = pre_race_results.copy() for race_id in tqdm(race_id_list): if race_id in race_results.keys(): continue try: url="https://db.netkeiba.com/race/" + race_id race_results[race_id] = pd.read_html(url)[4] time.sleep(1) except IndexError: continue except Exception as e: print(e) break except: break return race_results race_id_list=[] for place in range(1,11,1): for kai in range(1,6,1): for day in range(1,13,1): for r in range(1,13,1): race_id="2021"+str(place).zfill(2)+str(kai).zfill(2)+str(day).zfill(2)+str(r).zfill(2) race_id_list.append(race_id) test3 = scrape_race_results(race_id_list) for key in test3: test3[key].index = [key]*len(test3[key]) results = pd.concat([test3[key] for key in test3],sort=False)
回答2件
あなたの回答
tips
プレビュー
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。