为什么我在计算波动率时得到 NaN?
Why I got NaN when computing volatility?
我正在尝试遵循本文 here 中的方程式,计算功率时间序列数据的历史波动率。
数据统计说明如下:
count 9855.000000
mean 291.135088
std 187.503344
min 0.000000
25% 112.408512
50% 332.370871
75% 449.527323
max 601.370058
这是我的实现:
# Computing Volatility
window_size=27
VOLATILITY = pd.DataFrame()
VOLATILITY['PV']= data
#'intra-hour
# Compute the logarithmic value
VOLATILITY['Log_IA'] = np.log(VOLATILITY['PV'] / VOLATILITY['PV'].shift(1))
# Compute Volatility using the pandas rolling standard deviation function
VOLATILITY['intra-hour'] = VOLATILITY['Log_IA'].rolling(window=window_size).std() * np.sqrt(window_size)# *100
我的数据有 1 年的半小时观察,每天 27 步
这是我在 1 个存在 NaN 问题的选定日期获得的输出示例
Timestamp PV Log_IA intra-hour
2019-03-01 06:00:00 0.000000 NaN NaN
2019-03-01 06:30:00 2.946333 inf NaN
2019-03-01 07:00:00 20.963667 1.962229 NaN
2019-03-01 07:30:00 38.284333 0.602250 NaN
2019-03-01 08:00:00 38.224667 -0.001560 NaN
2019-03-01 08:30:00 54.486667 0.354475 NaN
2019-03-01 09:00:00 54.608333 0.002230 NaN
2019-03-01 09:30:00 55.290667 0.012418 NaN
2019-03-01 10:00:00 54.317333 -0.017761 NaN
2019-03-01 10:30:00 54.680333 0.006661 NaN
2019-03-01 11:00:00 42.142333 -0.260451 NaN
2019-03-01 11:30:00 44.569000 0.055986 NaN
2019-03-01 12:00:00 36.988333 -0.186436 NaN
2019-03-01 12:30:00 35.802000 -0.032599 NaN
2019-03-01 13:00:00 29.006667 -0.210478 NaN
2019-03-01 13:30:00 43.254333 0.399572 NaN
2019-03-01 14:00:00 45.246333 0.045024 NaN
2019-03-01 14:30:00 29.768333 -0.418676 NaN
2019-03-01 15:00:00 37.510667 0.231180 NaN
2019-03-01 15:30:00 31.937000 -0.160860 NaN
2019-03-01 16:00:00 39.990333 0.224873 NaN
2019-03-01 16:30:00 32.263000 -0.214717 NaN
2019-03-01 17:00:00 40.707333 0.232487 NaN
2019-03-01 17:30:00 14.551333 -1.028726 NaN
2019-03-01 18:00:00 10.294333 -0.346089 NaN
2019-03-01 18:30:00 2.552667 -1.394455 NaN
2019-03-01 19:00:00 0.036333 -4.252158 NaN
那么,为什么我会因为波动而得到 NaN?
我的实现有问题吗?
您的实现是这样的,无论 PV
的值如何,对于 Log_IA
的第零个值,您总是会得到 NaN
。这是转变的结果,可以通过 运行 以下代码段确认:
import numpy as np
import pandas as pd
VOLATILITY = pd.DataFrame()
VOLATILITY['PV'] = (1.0, 2.0, 3.0)
VOLATILITY['Log_IA'] = np.log(VOLATILITY['PV'] / VOLATILITY['PV'].shift(1))
您会看到 VOLATILITY
是:
PV Log_IA
0 1.0 NaN
1 2.0 0.693147
2 3.0 0.405465
Log_IA
的第零个值是 NaN
因为你用 除以 PV
的前一个值,即 PV
的值在索引 -1 处。这就是 shift()
所做的,但是索引 -1 处没有值,因此您得到 NaN
。您可以使用 fill_value
参数设置一个值来代替任何不存在的值:shift(1, fill_value=123)
。当前一个索引的 PV
值为 0 时,对于 Log_IA
的任何值,您还将获得 inf
。
那么,为什么 intra-hour
的所有值都得到 NaN
?您采用 VOLATILITY['Log_IA'].rolling(window=window_size)
的滚动标准差,其中在索引 0 处包含 inf
,而对于包含 inf
的序列,标准差未定义。所以滚动标准差是 NaN
,任何带有 NaN
的算术运算结果都是 NaN
.
现在,您的代码中的 也有问题。小于或等于 0 的值未定义对数,但这不是导致 NaN
s 的原因。
https://www.varsitytutors.com/hotmath/hotmath_help/topics/logarithmic-functions.html
我正在尝试遵循本文 here 中的方程式,计算功率时间序列数据的历史波动率。
数据统计说明如下:
count 9855.000000
mean 291.135088
std 187.503344
min 0.000000
25% 112.408512
50% 332.370871
75% 449.527323
max 601.370058
这是我的实现:
# Computing Volatility
window_size=27
VOLATILITY = pd.DataFrame()
VOLATILITY['PV']= data
#'intra-hour
# Compute the logarithmic value
VOLATILITY['Log_IA'] = np.log(VOLATILITY['PV'] / VOLATILITY['PV'].shift(1))
# Compute Volatility using the pandas rolling standard deviation function
VOLATILITY['intra-hour'] = VOLATILITY['Log_IA'].rolling(window=window_size).std() * np.sqrt(window_size)# *100
我的数据有 1 年的半小时观察,每天 27 步
这是我在 1 个存在 NaN 问题的选定日期获得的输出示例
Timestamp PV Log_IA intra-hour
2019-03-01 06:00:00 0.000000 NaN NaN
2019-03-01 06:30:00 2.946333 inf NaN
2019-03-01 07:00:00 20.963667 1.962229 NaN
2019-03-01 07:30:00 38.284333 0.602250 NaN
2019-03-01 08:00:00 38.224667 -0.001560 NaN
2019-03-01 08:30:00 54.486667 0.354475 NaN
2019-03-01 09:00:00 54.608333 0.002230 NaN
2019-03-01 09:30:00 55.290667 0.012418 NaN
2019-03-01 10:00:00 54.317333 -0.017761 NaN
2019-03-01 10:30:00 54.680333 0.006661 NaN
2019-03-01 11:00:00 42.142333 -0.260451 NaN
2019-03-01 11:30:00 44.569000 0.055986 NaN
2019-03-01 12:00:00 36.988333 -0.186436 NaN
2019-03-01 12:30:00 35.802000 -0.032599 NaN
2019-03-01 13:00:00 29.006667 -0.210478 NaN
2019-03-01 13:30:00 43.254333 0.399572 NaN
2019-03-01 14:00:00 45.246333 0.045024 NaN
2019-03-01 14:30:00 29.768333 -0.418676 NaN
2019-03-01 15:00:00 37.510667 0.231180 NaN
2019-03-01 15:30:00 31.937000 -0.160860 NaN
2019-03-01 16:00:00 39.990333 0.224873 NaN
2019-03-01 16:30:00 32.263000 -0.214717 NaN
2019-03-01 17:00:00 40.707333 0.232487 NaN
2019-03-01 17:30:00 14.551333 -1.028726 NaN
2019-03-01 18:00:00 10.294333 -0.346089 NaN
2019-03-01 18:30:00 2.552667 -1.394455 NaN
2019-03-01 19:00:00 0.036333 -4.252158 NaN
那么,为什么我会因为波动而得到 NaN?
我的实现有问题吗?
您的实现是这样的,无论 PV
的值如何,对于 Log_IA
的第零个值,您总是会得到 NaN
。这是转变的结果,可以通过 运行 以下代码段确认:
import numpy as np
import pandas as pd
VOLATILITY = pd.DataFrame()
VOLATILITY['PV'] = (1.0, 2.0, 3.0)
VOLATILITY['Log_IA'] = np.log(VOLATILITY['PV'] / VOLATILITY['PV'].shift(1))
您会看到 VOLATILITY
是:
PV Log_IA
0 1.0 NaN
1 2.0 0.693147
2 3.0 0.405465
Log_IA
的第零个值是 NaN
因为你用 除以 PV
的前一个值,即 PV
的值在索引 -1 处。这就是 shift()
所做的,但是索引 -1 处没有值,因此您得到 NaN
。您可以使用 fill_value
参数设置一个值来代替任何不存在的值:shift(1, fill_value=123)
。当前一个索引的 PV
值为 0 时,对于 Log_IA
的任何值,您还将获得 inf
。
那么,为什么 intra-hour
的所有值都得到 NaN
?您采用 VOLATILITY['Log_IA'].rolling(window=window_size)
的滚动标准差,其中在索引 0 处包含 inf
,而对于包含 inf
的序列,标准差未定义。所以滚动标准差是 NaN
,任何带有 NaN
的算术运算结果都是 NaN
.
现在,您的代码中的 也有问题。小于或等于 0 的值未定义对数,但这不是导致 NaN
s 的原因。
https://www.varsitytutors.com/hotmath/hotmath_help/topics/logarithmic-functions.html