QUANTAXIS ANALYSIS 行情分析/研究

  • 主要是针对行情的各种统计学特征/指标等分析
  • 支持QA_DataStruct_系列的add_func()功能
  • 接收DataFrame形式的行情以及QUANTAXIS.QADATA格式的行情
In [1]:
import QUANTAXIS as QA
you are using non-interactive mdoel quantaxis
In [ ]:
class QAAnalysis_stock():
    """
    行情分析器
    计算所有的指标
    """

    def __init__(self, dataStruct, *args, **kwargs):
        try:
            # 如果是QA_Data_系列
            self.data = dataStruct.data
            self._data = dataStruct
        except AttributeError:
            # 如果是dataframe
            self.data = dataStruct

        # self.data=DataSturct.data

    def __repr__(self):
        return '< QAAnalysis_Stock >'

    def __call__(self):
        return self.data

    # 使用property进行懒运算

    @property
    def open(self):
        return self.data['open']

    @property
    def high(self):
        return self.data['high']

    @property
    def low(self):
        return self.data['low']

    @property
    def close(self):
        return self.data['close']

    @property
    def vol(self):
        if 'volume' in self.data.columns:
            return self.data['volume']
        else:
            return self.data['vol']

    @property
    def volume(self):
        if 'volume' in self.data.columns:
            return self.data['volume']
        else:
            return self.data['vol']

    @property
    def date(self):

        return self.data.index.levels[self.data.index.names.index(
            'date')] if 'date' in self.data.index.names else self.data['date']

    @property
    def datetime(self):

        return self.data.index.levels[self.data.index.names.index(
            'datetime')] if 'datetime' in self.data.index.names else self.data.index.levels[self.data.index.names.index(
                'date')]

    @property
    def index(self):
        return self.data.index

    # 均价
    @property
    def price(self):
        return 0.25 * (self.open + self.close + self.high + self.low)

    @property
    def max(self):
        return self.price.max()

    @property
    def min(self):
        return self.price.min()

    @property
    def mean(self):
        return self.price.mean()
    # 一阶差分序列

    @property
    def price_diff(self):
        return self.price.diff(1)

    # 样本方差(无偏估计) population variance
    @property
    def pvariance(self):
        return statistics.pvariance(self.price)

    # 方差
    @property
    def variance(self):

        return statistics.variance(self.price)
    # 标准差

    @property
    def day_pct_change(self):
        return (self.open - self.close) / self.open

    @property
    def stdev(self):

        return statistics.stdev(self.price)
    # 样本标准差

    @property
    def pstdev(self):
        return statistics.pstdev(self.price)

    # 调和平均数
    @property
    def mean_harmonic(self):
        return statistics.harmonic_mean(self.price)

    # 众数
    @property
    def mode(self):
        return statistics.mode(self.price)

    # 波动率

    # 振幅
    @property
    def amplitude(self):
        return self.max - self.min
    # 偏度 Skewness

    @property
    def skewnewss(self):
        return self.price.skew()
    # 峰度Kurtosis

    @property
    def kurtosis(self):
        return self.price.kurt()
    # 百分数变化

    @property
    def pct_change(self):
        return self.price.pct_change()

    # 平均绝对偏差
    @property
    def mad(self):
        return self.price.mad()

    # 函数 指标计算
    @lru_cache()
    def add_func(self, func, *arg, **kwargs):
        return func(self.data, *arg, **kwargs)
In [54]:
data=QA.QA_fetch_stock_day_adv('300872','2020-01-01','2021-09-15') #[可选to_qfq(),to_hfq()]
s=QA.QAAnalysis_stock(data)

开盘价序列

In [55]:
    @property
    def open(self):
        return self.data['open']
In [56]:
s.open 
Out[56]:
date        code  
2020-08-24  300872    46.69
2020-08-25  300872    66.15
2020-08-26  300872    78.50
2020-08-27  300872    73.01
2020-08-28  300872    58.00
                      ...  
2021-09-08  300872    32.71
2021-09-09  300872    32.98
2021-09-10  300872    32.28
2021-09-13  300872    32.35
2021-09-14  300872    32.20
Name: open, Length: 260, dtype: float64

收盘价序列

In [57]:
    @property
    def close(self):
        return self.data['close']
In [58]:
s.close
Out[58]:
date        code  
2020-08-24  300872    76.53
2020-08-25  300872    82.10
2020-08-26  300872    70.99
2020-08-27  300872    60.00
2020-08-28  300872    52.15
                      ...  
2021-09-08  300872    33.15
2021-09-09  300872    32.45
2021-09-10  300872    32.54
2021-09-13  300872    31.92
2021-09-14  300872    31.77
Name: close, Length: 260, dtype: float64

最高价序列

In [59]:
    @property
    def high(self):
        return self.data['high']
In [60]:
s.high
Out[60]:
date        code  
2020-08-24  300872    98.00
2020-08-25  300872    90.77
2020-08-26  300872    82.00
2020-08-27  300872    74.00
2020-08-28  300872    58.85
                      ...  
2021-09-08  300872    33.29
2021-09-09  300872    33.11
2021-09-10  300872    32.98
2021-09-13  300872    32.57
2021-09-14  300872    32.67
Name: high, Length: 260, dtype: float64

最低价序列

In [61]:
    @property
    def low(self):
        return self.data['low']
In [62]:
s.low 
Out[62]:
date        code  
2020-08-24  300872    46.69
2020-08-25  300872    66.10
2020-08-26  300872    69.98
2020-08-27  300872    58.97
2020-08-28  300872    52.01
                      ...  
2021-09-08  300872    32.58
2021-09-09  300872    32.42
2021-09-10  300872    32.00
2021-09-13  300872    31.92
2021-09-14  300872    31.64
Name: low, Length: 260, dtype: float64

In [63]:
    @property
    def vol(self):
        if 'volume' in self.data.columns:
            return self.data['volume']
        else:
            return self.data['vol']
In [64]:
s.vol  
Out[64]:
date        code  
2020-08-24  300872    337942.0
2020-08-25  300872    335380.0
2020-08-26  300872    216283.0
2020-08-27  300872    198959.0
2020-08-28  300872    164599.0
                        ...   
2021-09-08  300872     33459.0
2021-09-09  300872     26253.0
2021-09-10  300872     29084.0
2021-09-13  300872     22417.0
2021-09-14  300872     26838.0
Name: volume, Length: 260, dtype: float64

同vol

In [65]:
s.volume
Out[65]:
date        code  
2020-08-24  300872    337942.0
2020-08-25  300872    335380.0
2020-08-26  300872    216283.0
2020-08-27  300872    198959.0
2020-08-28  300872    164599.0
                        ...   
2021-09-08  300872     33459.0
2021-09-09  300872     26253.0
2021-09-10  300872     29084.0
2021-09-13  300872     22417.0
2021-09-14  300872     26838.0
Name: volume, Length: 260, dtype: float64

日期

In [66]:
    @property
    def datetime(self):

        return self.data.index.levels[self.data.index.names.index(
            'datetime')] if 'datetime' in self.data.index.names else self.data.index.levels[self.data.index.names.index('date')]
In [67]:
s.date
Out[67]:
DatetimeIndex(['2020-08-24', '2020-08-25', '2020-08-26', '2020-08-27',
               '2020-08-28', '2020-08-31', '2020-09-01', '2020-09-02',
               '2020-09-03', '2020-09-04',
               ...
               '2021-09-01', '2021-09-02', '2021-09-03', '2021-09-06',
               '2021-09-07', '2021-09-08', '2021-09-09', '2021-09-10',
               '2021-09-13', '2021-09-14'],
              dtype='datetime64[ns]', name='date', length=260, freq=None)

时间

In [68]:
s.datetime
Out[68]:
DatetimeIndex(['2020-08-24', '2020-08-25', '2020-08-26', '2020-08-27',
               '2020-08-28', '2020-08-31', '2020-09-01', '2020-09-02',
               '2020-09-03', '2020-09-04',
               ...
               '2021-09-01', '2021-09-02', '2021-09-03', '2021-09-06',
               '2021-09-07', '2021-09-08', '2021-09-09', '2021-09-10',
               '2021-09-13', '2021-09-14'],
              dtype='datetime64[ns]', name='date', length=260, freq=None)

索引

In [69]:
    @property
    def index(self):
        return self.data.index
In [70]:
s.index
Out[70]:
MultiIndex([('2020-08-24', '300872'),
            ('2020-08-25', '300872'),
            ('2020-08-26', '300872'),
            ('2020-08-27', '300872'),
            ('2020-08-28', '300872'),
            ('2020-08-31', '300872'),
            ('2020-09-01', '300872'),
            ('2020-09-02', '300872'),
            ('2020-09-03', '300872'),
            ('2020-09-04', '300872'),
            ...
            ('2021-09-01', '300872'),
            ('2021-09-02', '300872'),
            ('2021-09-03', '300872'),
            ('2021-09-06', '300872'),
            ('2021-09-07', '300872'),
            ('2021-09-08', '300872'),
            ('2021-09-09', '300872'),
            ('2021-09-10', '300872'),
            ('2021-09-13', '300872'),
            ('2021-09-14', '300872')],
           names=['date', 'code'], length=260)

平均价(O+H+L+C)/4

In [71]:
    # 均价
    @property
    def price(self):
        return 0.25 * (self.open + self.close + self.high + self.low)
In [72]:
s.price
Out[72]:
date        code  
2020-08-24  300872    66.9775
2020-08-25  300872    76.2800
2020-08-26  300872    75.3675
2020-08-27  300872    66.4950
2020-08-28  300872    55.2525
                       ...   
2021-09-08  300872    32.9325
2021-09-09  300872    32.7400
2021-09-10  300872    32.4500
2021-09-13  300872    32.1900
2021-09-14  300872    32.0700
Length: 260, dtype: float64

price 的平均数

In [73]:
    @property
    def mean(self):
        return self.price.mean()
In [74]:
s.mean
Out[74]:
39.904500000000006

price 的最大值

In [75]:
    @property
    def max(self):
        return self.price.max()
In [76]:
s.max
Out[76]:
76.28

price 的最小值

In [27]:
    @property
    def min(self):
        return self.price.min()
In [28]:
s.min
Out[28]:
29.909999999999997

price 的平均绝对偏差

  • Mean Absolute Deviation
  • 平均绝对离差(mean absolute deviation)简称“平均离差”
  • 当总体的单位数为 N 时,有变量 X1,X2,X3,……,XN一1,XN
  • 各项变量总体平均数之差叫离差
  • 平均绝对离差定义:为各数据与平均值的离差的绝对值的平均数
In [29]:
    # 平均绝对偏差
    @property
    def mad(self):
        return self.price.mad()
In [30]:
s.mad
Out[30]:
6.63717307692308

price 的众数(没啥用)

In [77]:
    # 众数
    @property
    def mode(self):
        return statistics.mode(self.price)
In [78]:
s.mode
Out[78]:
66.97749999999999

price 的一阶差分

In [79]:
    # 一阶差分序列

    @property
    def price_diff(self):
        return self.price.diff(1)
In [80]:
s.price_diff
Out[80]:
date        code  
2020-08-24  300872        NaN
2020-08-25  300872     9.3025
2020-08-26  300872    -0.9125
2020-08-27  300872    -8.8725
2020-08-28  300872   -11.2425
                       ...   
2021-09-08  300872     0.0600
2021-09-09  300872    -0.1925
2021-09-10  300872    -0.2900
2021-09-13  300872    -0.2600
2021-09-14  300872    -0.1200
Length: 260, dtype: float64

price 的方差

In [81]:
    # 方差
    @property
    def variance(self):
        return statistics.variance(self.price)
In [82]:
s.variance 
Out[82]:
69.37130583011583

price 的样本方差

In [83]:
    # 样本方差(无偏估计) population variance
    @property
    def pvariance(self):
        return statistics.pvariance(self.price)
In [84]:
s.pvariance
Out[84]:
69.10449311538461

price 的标准差

In [85]:
    # 标准差
    @property
    def stdev(self):
        return statistics.stdev(self.price)
In [86]:
s.stdev
Out[86]:
8.328943860425271

price 的样本标准差

In [87]:
    # 样本标准差
    @property
    def pstdev(self):
        return statistics.pstdev(self.price)
In [88]:
s.pstdev
Out[88]:
8.312911229851105

price 的调和平均数

In [89]:
    # 调和平均数
    @property
    def mean_harmonic(self):
        return statistics.harmonic_mean(self.price)
In [90]:
s.mean_harmonic
Out[90]:
38.493185546318685

price 的振幅[极差]

In [91]:
    # 振幅
    @property
    def amplitude(self):
        return self.max - self.min
In [92]:
s.amplitude
Out[92]:
46.370000000000005

price 的峰度 (4阶中心距)

In [93]:
    # 偏度 Skewness

    @property
    def skewnewss(self):
        return self.price.skew()
In [94]:
s.skewnewss
Out[94]:
1.4109494377363532

price 的偏度 (3阶中心距)

In [95]:
    # 峰度Kurtosis
    @property
    def kurtosis(self):
        return self.price.kurt()
In [97]:
s.kurtosis
Out[97]:
2.156590388276748

price 的百分比变化序列

In [49]:
    # 百分数变化
    @property
    def pct_change(self):
        return self.price.pct_change()
In [98]:
s.pct_change 
Out[98]:
date        code  
2020-08-24  300872         NaN
2020-08-25  300872    0.138890
2020-08-26  300872   -0.011963
2020-08-27  300872   -0.117723
2020-08-28  300872   -0.169073
                        ...   
2021-09-08  300872    0.001825
2021-09-09  300872   -0.005845
2021-09-10  300872   -0.008858
2021-09-13  300872   -0.008012
2021-09-14  300872   -0.003728
Length: 260, dtype: float64

函数指标计算

In [101]:
    @lru_cache()
    def add_func(self, func, *arg, **kwargs):
        return func(self.data, *arg, **kwargs)

指标计算, 和DataStruct用法一致

In [99]:
s.add_func(QA.QA_indicator_CCI)
Out[99]:
CCI a b
date code
2020-08-24 300872 NaN 100 -100
2020-08-25 300872 NaN 100 -100
2020-08-26 300872 NaN 100 -100
2020-08-27 300872 NaN 100 -100
2020-08-28 300872 NaN 100 -100
... ... ... ... ...
2021-09-08 300872 167.881484 100 -100
2021-09-09 300872 86.993291 100 -100
2021-09-10 300872 44.500035 100 -100
2021-09-13 300872 -37.419768 100 -100
2021-09-14 300872 -60.101682 100 -100

260 rows × 3 columns