回答編集履歴

1

解説を追加

2018/05/28 00:18

投稿

magichan
magichan

スコア15898

test CHANGED
@@ -25,3 +25,157 @@
25
25
  data.to_csv('out.csv', index=None)
26
26
 
27
27
  ```
28
+
29
+
30
+
31
+ ---
32
+
33
+
34
+
35
+ **【補足】**
36
+
37
+
38
+
39
+ 簡単に説明します。
40
+
41
+
42
+
43
+ まず [1,2,3,4,5,6,7,8,9] といった1次元配列(pandas.Series)があった場合、RMSは
44
+
45
+
46
+
47
+ ```Python
48
+
49
+ import pandas as pd
50
+
51
+ import numpy as np
52
+
53
+
54
+
55
+ row_data = pd.Series([1,2,3,4,5,6,7,8,9])
56
+
57
+ res = np.sqrt((row_data ** 2).sum() / row_data.size)
58
+
59
+ print(res)
60
+
61
+ #5.627314338711377
62
+
63
+ ```
64
+
65
+
66
+
67
+ で求めることができますので、このRMSを求める式を ``lambda``で関数化しておいて
68
+
69
+
70
+
71
+ ```Python
72
+
73
+ import pandas as pd
74
+
75
+ import numpy as np
76
+
77
+
78
+
79
+ row_data = pd.Series([1,2,3,4,5,6,7,8,9])
80
+
81
+ rms = lambda d: np.sqrt((d ** 2).sum() / d.size)
82
+
83
+
84
+
85
+ res = rms(row_data)
86
+
87
+ print(res)
88
+
89
+ #5.627314338711377
90
+
91
+ ```
92
+
93
+ となります。
94
+
95
+
96
+
97
+ 次に、今回の質問のコードの場合、列全体のRMSを求めるのではなく一定区間のRMSをずらしながら求めることが要求されておりますので、この部分は``Series.rolling()`` を使用することになります。
98
+
99
+ ``Series.rolling()`` を簡単なサンプルで説明すると、例えば [1,2,3,4,5,6,7,8,9] といった1次元配列に対して``rolling().sum()`` を適用するとにより
100
+
101
+ ```Python
102
+
103
+ row_data = pd.Series([1,2,3,4,5,6,7,8,9])
104
+
105
+ res = row_data.rolling(window=3).sum()
106
+
107
+ print(res)
108
+
109
+ #0 NaN
110
+
111
+ #1 NaN
112
+
113
+ #2 6.0
114
+
115
+ #3 9.0
116
+
117
+ #4 12.0
118
+
119
+ #5 15.0
120
+
121
+ #6 18.0
122
+
123
+ #7 21.0
124
+
125
+ #8 24.0
126
+
127
+ #dtype: float64
128
+
129
+ ```
130
+
131
+
132
+
133
+ のように、一定区間(今回はwindow=3で指定した区間)毎の合計を求めることができます。
134
+
135
+ 今回の場合は一定区間毎の合計では無く、自作した関数(rms)を適用したいので、``Series.rolling().apply()``を使用して
136
+
137
+
138
+
139
+ ```Python
140
+
141
+ row_data = pd.Series([1,2,3,4,5,6,7,8,9])
142
+
143
+
144
+
145
+ rms = lambda d: np.sqrt((d ** 2).sum() / d.size)
146
+
147
+ res = row_data.rolling(window=3).apply(rms)
148
+
149
+ print(res)
150
+
151
+ #0 NaN
152
+
153
+ #1 NaN
154
+
155
+ #2 2.160247
156
+
157
+ #3 3.109126
158
+
159
+ #4 4.082483
160
+
161
+ #5 5.066228
162
+
163
+ #6 6.055301
164
+
165
+ #7 7.047458
166
+
167
+ #8 8.041559
168
+
169
+ #dtype: float64
170
+
171
+ ```
172
+
173
+ となります。
174
+
175
+
176
+
177
+ 最後に、rollingのパラメータですが、上記の例では ``index=0,1`` の箇所の結果が``NaN``になっております。これはこの部分を計算するための入力データの数が区間数(Window=3)を満たしておらず計算が出来ないためです。そこで``min_periods=1`` をパラメータで渡し、入力データが最低でも1つあれば計算を行うよう指定しております。さらに上記の例では 入力データ``index=0,1,2``の結果が``index=2``に入っております。そこで``center=True``を渡す事により index=0,1,2の結果が index=1 に出力されるようにしております。
178
+
179
+
180
+
181
+ 以上です。