我有一個資料框,其中包含我最近一次運行的資料點(通過 Strava API)。資料框有兩列:
| time_elapsed | distance_covered |
-----------------------------------
| 1 | 1.1 |
| 2 | 2.3 |
| 3 | 3.2 |
...
| 5876 | 15200.3 |
兩列都是累積的。我現在想找到我在鍛煉程序中跑過的最快的 5 公里,即連續行的子集,這樣
row[-1]['distance_covered']-row[0]['distance_covered'] >= 5000row[-1]['time_elapsed'] - row[0]['time_elapsed']被最小化
我下面的解決方案正在作業;但是它相當慢并且感覺不是特別優雅,因為我基本上多次迭代相同的行。
distance_time = defaultdict(list)
for i in range(df.shape[0]):
working_df = df.iloc[i:].copy()
previous = df.iloc[i]['distance_covered']
working_df['distance_covered'] = working_df['distance_covered'] - previous
ix = np.argmax(working_df['distance_covered'] > 5000)
if ix == 0:
break
else:
distance_time[5000].append(working_df.iloc[ix]['time_elapsed'] - working_df.iloc[0]['time_elapsed'])
fastest_time = np.nanmin(distance_time[5000])
另一種方法是計算間隔時間,然后使用 cumsum,但我仍然需要從每個可能的起始行查看資料幀,所以我認為它不會更快。
有沒有人有更好的想法/更快的方法來實作相同的結果?
編輯: df.head(10).to_dict() 的實際示例輸出
{'time_elapsed': {0: 1, 1: 2, 2: 3, 3: 4, 4: 5, 5: 6, 6: 7, 7: 8, 8: 9}, 'distance_covered': {0: 1.1, 1: 2.3, 2: 4.4, 3: 7.1, 4: 9.7, 5: 12.3, 6: 15.6, 7: 18.7, 8: 21.7}}
uj5u.com熱心網友回復:
設定
df = pd.DataFrame(
{
'time_elapsed': {0: 1, 1: 2, 2: 3, 3: 4, 4: 5, 5: 6, 6: 7, 7: 8, 8: 9},
'distance_covered': {0: 1.1, 1: 2.3, 2: 4.4, 3: 7.1, 4: 9.7, 5: 12.3, 6: 15.6, 7: 18.7, 8: 21.7}
},
)
解決方案
下面我假設時間以秒為單位,距離以米為單位。問題中沒有說明這一點,如果不正確,則需要進行調整。
插入初始點:
df.iloc[-1,:] = [0,0]
設定distance_covered為索引,然后以 0.1m (10cm) 的間隔重新索引并插入時間列。當索引是基于時間的時,這類似于“重新采樣”
interpolated = (
df
.set_index("distance_covered")
.sort_index()
.reindex(np.arange(0,int(df["distance_covered"].max()) 1, 0.1))
.interpolate()
)
`interpolated 是具有單列的資料框。看起來像這樣
time_elapsed
distance_covered
0.0 0.000000
0.1 0.090909
0.2 0.181818
0.3 0.272727
0.4 0.363636
... ...
18.5 7.937500
18.6 7.968750
18.7 8.000000
18.8 8.000000
18.9 8.000000
資料仍然是累積的,所以讓我們取連續值之間的差,然后做 50000 行的滾動求和 = 50000 x 0.1m = 5km
interpolated["time_elapsed"].diff().rolling(50000).sum()
這將為您提供一個系列,按所覆寫的距離進行索引,這些值是用于覆寫前 5 公里的時間。從那里找到您的系列(或情節等)中的最大值
uj5u.com熱心網友回復:
如果 Python 的 while 回圈不是很慢(與 Cython/C 相比),您可以使用滑動視窗解決此問題。該解決方案的時間復雜度為 O(n),因為序列中的每個元素最多被訪問兩次:一次由結束指標訪問i,一次由開始指標訪問j。
i = 0
j = 0
dist = df['distance_covered']
time = df['time_elapsed']
res = []
while i < len(df):
while i < len(df) and dist.iloc[i] - dist.iloc[j] < 5000:
i = i 1
if i == len(df):
break
while j < i and dist.iloc[i] - dist.iloc[j] >= 5000:
if not res or time.iloc[res[1]] - time.iloc[res[0]] > time.iloc[i] - time.iloc[j]:
res = [j, i]
j = j 1
轉載請註明出處,本文鏈接:https://www.uj5u.com/shujuku/516751.html
標籤:Python熊猫表现
上一篇:Android(Kotlin)MaterialDesignDateRangePicker如何正確設定最小和最大日期?
