我们能否在Python中对多元时间序列数据集进行聚类?

4

我有一个数据集,其中包含不同股票在不同时期的许多财务信号值。例如:

StockName  Date   Signal1  Signal2
----------------------------------
Stock1     1/1/20    a       b
Stock1     1/2/20    c       d
.
.
.
Stock2     1/1/20    e       f
Stock2     1/2/20    g       h
.
.
.

我想创建一个类似下面的时间序列表,并根据信号1和信号2(2个变量)对股票进行聚类。
StockName   1/1/20    1/2/20    ........    Cluster#
----------------------------------------------------
 Stock1     [a,b]      [c,d]                    0
 Stock2     [e,f]      [g,h]                    1
 Stock3     ......     .....                    0
 .
 .
 .

1) 有没有办法做到这一点?(根据多个变量对时间序列数据进行聚类股票)我尝试在线搜索,但它们都是关于基于一个变量对时间序列进行聚类。

2) 同样,是否有任何方法在不同的时间聚类不同的股票? (因此,可能在时间1的Stock1与时间3的Stock2处于相同的聚类中)


我们可以吗?当然可以:https://datascience.stackexchange.com/questions/29287/multivariate-time-series-clustering - Zabir Al Nazi
2个回答

2
我在这里修改我的答案,基于你最后发布的新信息。
from utils import *

import time
import numpy as np

from mxnet import nd, autograd, gluon
from mxnet.gluon import nn, rnn
import mxnet as mx
import datetime
import seaborn as sns
import matplotlib.pyplot as plt

# %matplotlib inline
from sklearn.decomposition import PCA

import math

from sklearn.preprocessing import MinMaxScaler
from sklearn.metrics import mean_squared_error
from sklearn.preprocessing import StandardScaler

import xgboost as xgb
from sklearn.metrics import accuracy_score

import warnings
warnings.filterwarnings("ignore")

context = mx.cpu(); model_ctx=mx.cpu()
mx.random.seed(1719)

# Note: The purpose of this section (3. The Data) is to show the data preprocessing and to give rationale for using different sources of data, hence I will only use a subset of the full data (that is used for training).

def parser(x):
    return datetime.datetime.strptime(x,'%Y-%m-%d')

# dataset_ex_df = pd.read_csv('data/panel_data_close.csv', header=0, parse_dates=[0], date_parser=parser)


import yfinance as yf

# Get the data for the stock AAPL
start = '2018-01-01'
end = '2020-04-22'

data = yf.download('GS', start, end)

data = data.reset_index()
data

enter image description here

    data.dtypes

    # re-name field from 'Adj Close' to 'Adj_Close'
    data = data.rename(columns={"Adj Close": "Adj_Close"})
    data

num_training_days = int(data.shape[0]*.7)
print('Number of training days: {}. Number of test days: {}.'.format(num_training_days, data.shape[0]-num_training_days))



# TECHNICAL INDICATORS
#def get_technical_indicators(dataset):
# Create 7 and 21 days Moving Average
data['ma7'] = data['Adj_Close'].rolling(window=7).mean()
data['ma21'] = data['Adj_Close'].rolling(window=21).mean()


# Create exponential weighted moving average
data['26ema'] = data['Adj_Close'].ewm(span=26).mean()
data['12ema'] = data['Adj_Close'].ewm(span=12).mean()
data['MACD'] = (data['12ema']-data['26ema'])

# Create Bollinger Bands
data['20sd'] = data['Adj_Close'].rolling(window=20).std() 
data['upper_band'] = data['ma21'] + (data['20sd']*2)
data['lower_band'] = data['ma21'] - (data['20sd']*2)

# Create Exponential moving average
data['ema'] = data['Adj_Close'].ewm(com=0.5).mean()

# Create Momentum
data['momentum'] = data['Adj_Close']-1



dataset_TI_df = data
dataset = data


def plot_technical_indicators(dataset, last_days):
    plt.figure(figsize=(16, 10), dpi=100)
    shape_0 = dataset.shape[0]
    xmacd_ = shape_0-last_days

    dataset = dataset.iloc[-last_days:, :]
    x_ = range(3, dataset.shape[0])
    x_ =list(dataset.index)

    # Plot first subplot
    plt.subplot(2, 1, 1)
    plt.plot(dataset['ma7'],label='MA 7', color='g',linestyle='--')
    plt.plot(dataset['Adj_Close'],label='Closing Price', color='b')
    plt.plot(dataset['ma21'],label='MA 21', color='r',linestyle='--')
    plt.plot(dataset['upper_band'],label='Upper Band', color='c')
    plt.plot(dataset['lower_band'],label='Lower Band', color='c')
    plt.fill_between(x_, dataset['lower_band'], dataset['upper_band'], alpha=0.35)
    plt.title('Technical indicators for Goldman Sachs - last {} days.'.format(last_days))
    plt.ylabel('USD')
    plt.legend()

    # Plot second subplot
    plt.subplot(2, 1, 2)
    plt.title('MACD')
    plt.plot(dataset['MACD'],label='MACD', linestyle='-.')
    plt.hlines(15, xmacd_, shape_0, colors='g', linestyles='--')
    plt.hlines(-15, xmacd_, shape_0, colors='g', linestyles='--')
    # plt.plot(dataset['log_momentum'],label='Momentum', color='b',linestyle='-')

    plt.legend()
    plt.show()

plot_technical_indicators(dataset_TI_df, 400)

enter image description here

这将给你一些可以使用的信号。当然,这些特征可以是任何你想要的。我相信你知道这是技术分析,而不是基本面分析。现在,你可以进行聚类或其他你想做的事情了。
这里有一个好的聚类链接。

https://www.pythonforfinance.net/2018/02/08/stock-clusters-using-k-means-algorithm-in-python/


嗨ASH,感谢您的评论。根据您附加的数据框,我想要实现的是每个单元格具有多个特征的数据框。(例如,2017-1-3中的MMM可能会为单个日期生成多个信号。);对于第二个问题,基于您附加的df,我想要实现的是像2017-1-3中的MMM与2017-1-4中的ABT在同一簇中(不同日期的不同股票可以聚类在一起)。 - Zhang Yongheng
啊,我明白了。好的,我认为我发送给你的链接将回答你的两个问题。试试吧,你会学到很多东西。如果你在某个地方卡住了,请回帖并详细说明你遇到的问题,我会尽力提供更多帮助。我认为你现在已经有所需了。 - ASH
嗨ASH,我看到这个例子确实计算了“回报率”和“波动率”。然而,我发现每个股票只对应一个“回报率”值和一个“波动率”值。我想做一些像你附加的数据框那样的事情。它反映了随时间变化的调整收盘价。我还想添加其他随时间变化的信号。因此,每个单元格不仅具有Adj.Close值,还具有不同的信号值。(每个单元格表示特定时间的一个股票)。因此,数据框变成了随时间变量的变化。 - Zhang Yongheng

1

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接