Python新闻比特币价格预测

在OTUS 的机器学习课程开始之前,准备了本文的翻译




任务


在本指南中,我们使用比特币与美元数据集



上面的数据集包含每日价格摘要,其中CHANGE列是价格相对于前一天价格(PRICE)对新价格OPEN的百分比变化

目标:为了简化任务,我们将集中于预测第二天价格是上涨(CHANGE> 0)还是下跌(CHANGE <0)。(因此我们可以潜在地使用``现实生活中的预测'')。

要求

  • 必须在系统上安装Python 2.6+或3.1+
  • 安装pandassklearnopenblender(使用pip)

$ pip install pandas OpenBlender scikit-learn


步骤1.获取比特币数据


首先,让我们导入必要的库:

import OpenBlender
import pandas as pd
import json


现在,通过OpenBlender API提取数据
首先,让我们定义参数(在我们的例子中,这只是比特币数据集ID ):

# It only contains the id, we'll add more parameters later.
parameters = { 
 'id_dataset':'5d4c3af79516290b01c83f51'
}

注意:您需要在openblender.io上创建一个帐户(免费)并添加令牌(您可以在“帐户”标签中找到该令牌):

parameters = {     
   'token':'your_token',
   'id_dataset':'5d4c3af79516290b01c83f51'
}

现在,让我们将数据放入Dataframe'df '中

# This function pulls the data and orders by timestamp
def pullObservationsToDF(parameters):
    action = 'API_getObservationsFromDataset'
    df = pd.read_json(json.dumps(OpenBlender.call(action,parameters)['sample']), convert_dates=False,convert_axes=False) .sort_values('timestamp', ascending=False)
    df.reset_index(drop=True, inplace=True)
    return df
df = pullObservationsToDF(parameters)

并查看它们:



注意:值可能会有所不同,因为数据集每天都会更新

步骤2.数据准备


首先,我们需要创建一个预测目标,即“ CHANGE ”是增加还是减少。为此,将'success_thr_over':0添加到目标阈值参数:

parameters = {
   'token':'your_token',   
   'id_dataset':'5d4c3af79516290b01c83f51',
   'target_threshold':{'feature':'change', 'success_thr_over': 0}
}

如果我们再次从API中提取数据:

df = pullObservationsToDF(parameters)
df.head() 



属性“ CHANGE”已由新属性“ change_over_0”替换,如果“ CHANGE”为正,则变为1,否则为0。这将是机器学习的目标。

如果我们要预测“明天”的观测,我们将无法使用明天的信息,因此我们加一个延迟时间。

parameters = { 
   'token':'your_token',
   'id_dataset':'5d4c3af79516290b01c83f51',
   'target_threshold':{'feature':'change','success_thr_over' : 0},
   'lag_target_feature':{'feature':'change_over_0', 'periods' : 1}
}
df = pullObservationsToDF(parameters)
df.head()



这只是将“ change_over_0”与前一天(期间)的数据对齐,并将其名称更改为“ TARGET_change_over_0”

让我们看一下依赖关系:

target_variable = 'TARGET_change_over_0'
df = df.dropna()
df.corr()[target_variable].sort_values()



它们是线性独立的,不太可能有用。

步骤3.获取商业新闻数据


OpenBlender中搜索依赖项之后,我发现了Fox商业新闻数据集,该数据集将有助于为目标生成良好的预测。



我们需要找到一种方法,通过计算新闻摘要中单词和单词组的重复次数,并将``标题''列的值转换为数字特征,并将它们与我们的比特币数据集进行及时比较。这比听起来容易。

首先,您需要为新闻“标题”属性创建一个TextVectorizer

action = 'API_createTextVectorizer'
vectorizer_parameters = {
    'token' : 'your_token',
    'name' : 'Fox Business TextVectorizer',
    'sources':[{'id_dataset' : '5d571f9e9516293a12ad4f6d',
                'features' : ['title']}],
    'ngram_range' : {'min' : 1, 'max' : 2},
    'language' : 'en',
    'remove_stop_words' : 'on',
    'min_count_limit' : 2
}

我们将创建一个矢量化程序,以数字形式将所有符号作为标记词获得。上面,我们指出了以下几点:

  • 名称:我们称其为“ Fox Business TextVectorizer”
  • anchor:数据集的ID和我们将需要用作源的特征的名称(在我们的情况下,仅是'title');
  • ngram_range:用于标记化的一组单词的最小和最大长度;
  • 语言:英语
  • remove_stop_words:从源中删除停用词;
  • min_count_limit:应该视为标记的最小重复次数(单次出现很少有用)。

现在运行:

res = OpenBlender.call(action, vectorizer_parameters)
res


回答:

{  
    'message' : 'TextVectorizer created successfully.'
    'id_textVectorizer' : '5dc1a404951629331f6359dd',
    'num_ngrams': 4270
}

创建了TextVectorizer,根据我们的配置生成了4270个n-gram。稍后,我们将需要生成的ID:

5dc1a404951629331f6359dd

步骤4.与比特币数据集兼容的新闻摘要


现在我们需要及时比较新闻摘要和比特币汇率数据。通常,这意味着您需要使用时间戳作为键来组合两组数据。让我们将合并的数据添加到原始数据提取选项中:

parameters = { 
   'token':'your_token',  
   'id_dataset':'5d4c3af79516290b01c83f51',
   'target_threshold' : {'feature':'change','success_thr_over':0},
   'lag_target_feature' : {'feature':'change_over_0', 'periods':1},
   'blends':[{'id_blend':'5dc1a404951629331f6359dd',
               'blend_type' : 'text_ts',
               'restriction' : 'predictive', 
               'specifications':{'time_interval_size' : 3600*12 }}]
}

上面,我们指出了以下几点:

  • id_blend:我们的textVectorizer的ID;
  • blend_type'text_ts',以便Python理解它是文本和时间戳的混合;
  • 限制“预测性”,因此将来的新闻不会与所有观察“混合”,而只能与在指定时间之前发布的那些“混合”。
  • blend_class'closest_observation',因此只有最接近的观测值才被“混合”;
  • 规格:用于传输观测值的最大可能经过时间,在这种情况下为12小时(3600 * 12)。这意味着将根据最近12个小时的新闻预测对比特币价格的每次观察。

最后,我们只是按日期添加过滤器“date_filter”日期,开始于8月20日,因为这是当福克斯新闻开始收集数据,并“drop_non_numeric”,使我们得到的只有数:

parameters = { 
   'token':'your_token',
   'id_dataset':'5d4c3af79516290b01c83f51',
   'target_threshold' : {'feature':'change','success_thr_over':0},
   'lag_target_feature' : {'feature':'change_over_0', 'periods':1},
   'blends':[{'id_blend':'5dc1a404951629331f6359dd',
               'blend_type' : 'text_ts',
               'restriction' : 'predictive',
               'blend_class' : 'closest_observation', 
               'specifications':{'time_interval_size' : 3600*12 }}],
   'date_filter':{'start_date':'2019-08-20T16:59:35.825Z',
                   'end_date':'2019-11-04T17:59:35.825Z'},
   'drop_non_numeric' : 1
}

注意:我将11月4日表示为'end_date',因为这是我编写此代码的日期,因此您可以更改日期。

让我们再次获取数据:

df = pullObservationsToDF(parameters)
print(df.shape)
df.head()

(57,2115)



现在,我们有2000多个带有标记和57个观察值的符号。

步骤5.将ML应用于预测目标


现在,最后,我们有了一个干净的数据集,它看起来完全符合我们的需要,并且具有目标和关联数值数据的时间偏移。

让我们看一下与“ Target_change_over_0”的最高相关性



现在,我们有了一些相关属性。让我们按时间顺序将数据集分为训练和测试,以便我们可以在早期观察中训练模型,在以后进行观察。

X = df.loc[:, df.columns != target_variable].values
y = df.loc[:,[target_variable]].values
div = int(round(len(X) * 0.29))
# We take the first observations as test and the last as train because the dataset is ordered by timestamp descending.
X_test = X[:div]
y_test = y[:div]
print(X_test.shape)
print(y_test.shape)
X_train = X[div:]
y_train = y[div:]
print(X_train.shape)
print(y_train.shape)



我们有40个观察值用于训练,而17个则用于测试。
现在我们导入必要的库:

from sklearn.ensemble import RandomForestRegressor
from sklearn.metrics import mean_squared_error
from sklearn.metrics import accuracy_score
from sklearn.metrics import roc_auc_score
from sklearn import metrics

现在,让我们使用随机森林(RandomForest)进行预测:

rf = RandomForestRegressor(n_estimators = 1000)
rf.fit(X_train, y_train)
y_pred = rf.predict(X_test)

为了更容易理解,我们将预测和y_test放入数据框:

df_res = pd.DataFrame({'y_test':y_test[:,0], 'y_pred':y_pred})
df_res.head()

我们真正的'y_test'是二进制的,但是我们的预测是float类型的,因此我们将它们四舍五入,假设如果它们大于0.5,则意味着价格上涨,如果小于0.5,则意味着下跌。

threshold = 0.5
preds = [1 if val > threshold else 0 for val in df_res['y_pred']]

现在,为了更好地理解结果,我们获得了AUC,误差矩阵和准确性指标:

print(roc_auc_score(preds, df_res['y_test']))
print(metrics.confusion_matrix(preds, df_res['y_test']))
print(accuracy_score(preds, df_res['y_test']))



使用0.65 AUC,可以得到正确预测的64.7%。

  • 我们预计会下降9倍,而价格也会下降(右);
  • 我们预测会下降5倍,并且价格(不正确地)上涨;
  • 我们预计会增加1次,但价格下降幅度却不正确);
  • 我们预测价格会上涨2倍,且价格会上涨(真实)。

了解有关该课程的更多信息

All Articles