当前位置: 首页 > news >正文

【机器学习实战中阶】比特币价格预测

在这里插入图片描述

比特币价格预测项目介绍

比特币价格预测项目是一个非常有实用价值的机器学习项目。随着区块链技术的快速发展,越来越多的数字货币如雨后春笋般涌现,尤其是比特币作为最早的加密货币,其价格波动备受全球投资者和研究者的关注。本项目的目标是通过分析比特币的历史数据,建立一个能够预测未来比特币价格的机器学习模型,帮助用户更好地理解和应对市场的波动。

项目背景

比特币(Bitcoin)是一种去中心化的数字货币,由中本聪(Satoshi Nakamoto)在2008年提出,并于2009年正式发布。与传统的法定货币不同,比特币不依赖于任何中央银行或金融机构,而是基于区块链技术,通过分布式账本记录所有的交易。比特币的总量被限制在2100万枚,这使得它具备了稀缺性,也为其价格波动提供了基础。

近年来,随着加密货币市场的迅速扩展,比特币的价格经历了多次剧烈波动。投资者、金融机构以及普通用户都对比特币的未来价格走势充满好奇。然而,由于比特币市场的高度不确定性,预测其价格变化并非易事。因此,通过机器学习技术来分析历史数据,进而预测比特币的价格走势,成为一个极具吸引力的项目。

项目目标

本项目的主要目标是通过机器学习模型来预测比特币的未来价格,具体目标包括以下几个方面:

  1. 数据收集与预处理:首先,项目需要收集大量的历史数据,包括比特币的每日价格(开盘价、收盘价、最高价、最低价)、交易量、市场情绪指数、宏观经济指标等。数据来源可以包括加密货币交易平台、新闻媒体、社交媒体等。收集到的数据需要进行清洗、标准化和特征提取,以确保输入模型的数据质量。

  2. 特征工程:在数据预处理的基础上,进行特征工程,提取对价格预测有帮助的特征。例如,时间序列特征(如移动平均线、波动率)、技术指标(如MACD、RSI)等。通过特征工程,可以更好地捕捉比特币价格变化的规律。

  3. 模型选择与训练:选择合适的机器学习算法来构建预测模型。常用的算法包括线性回归、随机森林、支持向量机(SVM)、长短期记忆网络(LSTM)等。由于比特币价格的预测是一个时间序列问题,LSTM等深度学习算法可能具有更好的表现。通过交叉验证和超参数调优,确保模型的准确性和鲁棒性。

  4. 模型评估与优化:使用历史数据对模型进行评估,通过均方误差(MSE)、平均绝对误差(MAE)等指标衡量模型的预测效果。同时,进行回测(Backtesting)来验证模型在不同时间段的表现,确保其在实际应用中的稳定性。

  5. 预测与应用:训练好的模型可以用于预测未来的比特币价格。通过可视化工具,用户可以直观地查看预测结果。此外,该模型还可以集成到加密货币交易系统中,帮助投资者制定交易策略。在实际应用中,用户可以根据模型的预测结果调整投资组合,降低市场风险。

项目意义

比特币价格预测项目不仅具有学术研究价值,还具备广泛的实际应用前景。对于投资者而言,准确的比特币价格预测可以帮助他们更好地把握市场机会,降低投资风险。对于金融机构和研究机构而言,该项目可以为加密货币市场的研究和监管提供重要的参考依据。

此外,随着区块链技术的不断发展,数字货币市场的规模和影响力也在不断扩大。比特币作为加密货币市场的风向标,其价格波动对整个市场都有着重大影响。通过该项目的研究,可以帮助我们更好地理解加密货币市场的运行规律,推动区块链技术的进一步发展。

技术难点与挑战

尽管比特币价格预测项目具有很大的潜力,但在实际操作中也面临着一些技术难点和挑战:

  1. 数据质量问题:比特币市场的数据来源复杂,数据质量参差不齐,可能包含缺失值、异常值等问题。如何有效地清洗和处理这些数据是一个重要的挑战。

  2. 市场的不确定性:比特币市场受到多种因素的影响,包括政策法规、市场情绪、技术进步等。这些因素的复杂性和不确定性使得价格预测变得异常困难。

  3. 模型的泛化能力:由于比特币价格的高波动性,模型需要在不同的市场环境下保持较好的预测能力。如何提高模型的泛化能力是一个重要的研究方向。

  4. 实时性要求:在实际应用中,模型需要能够实时处理和预测,这对计算能力和系统响应速度提出了较高的要求。

总结

比特币价格预测项目是一个结合了金融、数据科学和机器学习的综合性项目。通过分析历史数据并结合机器学习算法,项目旨在开发出一个准确、稳定的比特币价格预测模型。该模型不仅可以为个人投资者提供决策支持,还可以为金融机构和研究者提供有价值的市场分析工具。希望该项目能够为加密货币市场的进一步发展提供新的思路和方法。

接下来就开启我们的旅程吧!

序列模型介绍

序列模型是指那些处理数据序列的机器学习模型。序列数据包括文本流、音频片段、视频片段、时间序列数据等。递归神经网络(Recurrent Neural Networks, RNN)是序列模型中最受欢迎的算法之一。

以下代码导入了多个用于处理序列数据和绘图的模块,并设置了绘图库的基础配置。这段代码的主要目的是准备所需的库,以便后续处理数据和生成可视化图表。

from math import sqrt  # 从 math 模块中导入 sqrt 函数,用于计算平方根
from numpy import concatenate  # 从 NumPy 模块中导入 concatenate 函数,用于合并多个数组
from matplotlib import pyplot  # 导入 Matplotlib 的 Pyplot 模块,用于绘制数据图形
import pandas as pd  # 导入 Pandas 模块,用于数据处理和分析
from datetime import datetime  # 从 datetime 模块中导入 datetime 类,用于处理日期和时间
from sklearn.preprocessing import MinMaxScaler  # 从 sklearn.preprocessing 模块中导入 MinMaxScaler 类,用于数据归一化
from sklearn.preprocessing import LabelEncoder  # 从 sklearn.preprocessing 模块中导入 LabelEncoder 类,用于标签编码
from sklearn.metrics import mean_squared_error  # 从 sklearn.metrics 模块中导入 mean_squared_error 函数,用于计算均方误差# 以下代码导入了 Keras 库中的模型和层,用于构建递归神经网络(RNN)
from keras.models import Sequential  # 从 Keras 模块中导入 Sequential 类,用于构建顺序模型
'''Dense Layer 是一个简单的神经元层,其中每个神经元都从上一层的所有神经元接收输入,因此称为全连接层。Dense Layer 通常用于根据卷积层的输出对图像进行分类。'''
from keras.layers import Dense  # 从 Keras.layers 模块中导入 Dense 类,用于添加全连接层
from keras.layers import LSTM  # 从 Keras.layers 模块中导入 LSTM 类,用于添加长短时记忆层# 以下代码导入了 Plotly 库中的离线绘图模块,用于在 Jupyter Notebook 中离线绘制图表
'''使用 plotly.offline.iplot() 在离线状态下在 Jupyter Notebook 中显示图表。
注意 − 需要 Plotly 版本 1.9.4+ 才能进行离线绘图。
更改脚本中的 plot() 函数语句并运行。
将在本地创建一个名为 temp-plot.html 的 HTML 文件,并在浏览器中打开。'''
import plotly.offline as py  # 导入 Plotly 的离线模块,用于离线绘图'''The plotly. graph_objects 模块(通常导入为 go)包含一个自动生成的 Python 类层次结构,这些类代表了此图形模式中的非叶节点。
术语 "graph objects" 指的是这些类的实例。plotly 中定义的主要类。'''
import plotly.graph_objs as go  # 导入 Plotly 的 graph_objects 模块,用于创建绘图对象import numpy as np  # 导入 NumPy 模块,用于数值计算
import seaborn as sns  # 导入 Seaborn 模块,用于绘制统计图形# py.init_notebook_mode(connected=True)  # 这行代码允许我们在离线版本的 Plotly 中工作
# %matplotlib inline  # %matplotlib inline 命令告诉 IPython 环境在当前单元格之后立即绘制图表
代码总结

这段代码的主要目的是导入处理序列数据和生成可视化图表所需的库。具体来说:

  1. 数学运算:导入了 sqrt 函数,用于计算平方根。
  2. 数组操作:导入了 concatenate 函数,用于合并多个数组。
  3. 绘图:导入了 Matplotlib 的 pyplot 模块,用于绘制数据图形;导入了 Plotly 的 offline 模块,用于在 Jupyter Notebook 中离线绘制图表;导入了 Seaborn 模块,用于绘制统计图形。
  4. 数据处理:导入了 Pandas 模块,用于数据处理和分析;导入了 datetime 类,用于处理日期和时间。
  5. 数据预处理:导入了 MinMaxScaler 类,用于数据归一化;导入了 LabelEncoder 类,用于标签编码。
  6. 模型评估:导入了 mean_squared_error 函数,用于计算均方误差。
  7. 深度学习模型:导入了 Keras 库中的 Sequential 类,用于构建顺序模型;导入了 Dense 类,用于添加全连接层;导入了 LSTM 类,用于添加长短时记忆层。

读取数据集并进行可视化

以下代码读取数据集并进行基本的信息查看,然后绘制基于加权价格的折线图。接着,代码将加权价格中的 0 值替换为 NaN,并使用前向填充方法填充这些值,最后再次绘制折线图以显示填充后的数据。

# 读取数据集并进行基本的信息查看
data = pd.read_csv(filepath_or_buffer="../input/btcusdkraken/BTCUSDKRAKEN", index_col="Date")  # 从指定路径读取 CSV 文件,并将 "Date" 列设置为索引
data.info()  # 打印数据集的基本信息,包括每列的数据类型和非空值数量data.head()  # 显示数据集的前 5 行
data.tail()  # 显示数据集的最后 5 行# 绘制基于加权价格的折线图
btc_trace = go.Scatter(x=data.index, y=data['Weighted Price'], name='Price')  # 创建一个折线图数据对象,x 轴为日期,y 轴为加权价格,图例名称为 "Price"
py.iplot([btc_trace])  # 在 Jupyter Notebook 中显示折线图# 将加权价格中的 0 值替换为 NaN,然后使用前向填充方法填充这些值
data['Weighted Price'].replace(0, np.nan, inplace=True)  # 将加权价格列中的 0 值替换为 NaN
data['Weighted Price'].fillna(method='ffill', inplace=True)  # 使用前向填充方法(ffill)填充 NaN 值# 再次绘制基于加权价格的折线图,显示填充后的数据
btc_trace = go.Scatter(x=data.index, y=data['Weighted Price'], name='Price')  # 创建一个新的折线图数据对象,x 轴为日期,y 轴为加权价格,图例名称为 "Price"
py.iplot([btc_trace])  # 在 Jupyter Notebook 中显示新的折线图

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

使用加权价格作为特征训练 LSTM 模型

使用加权价格作为特征来训练 LSTM 模型。使用 MinMaxScaler 将加权价格归一化到 0 到 1 的范围内。然后将数据集的 70% 用于训练,30% 用于测试。接下来,创建一个函数来生成具有回溯窗口的数据集,并生成训练和测试数据集。为了训练模型,将 X 重塑为适合 LSTM 输入的形状。运行 LSTM 模型 300 个周期,并绘制损失曲线。使用测试数据进行预测,并绘制预测值与真实值的折线图。最后,将预测值和真实值反归一化为原始值,并计算 RMSE。再次绘制预测值与真实值的折线图,这次以美元为单位。将 X 转换为日期,并将预测值和真实值重塑为适合 Plotly 绘图的形状。最后,使用 Plotly 绘制预测值和真实值的折线图,其中 X 轴为日期,Y 轴为美元价格。

代码翻译及详细注释

读取数据集并进行归一化

代码总结
这段代码的主要目的是读取数据集中的加权价格,并使用 MinMaxScaler 将其归一化到 0 到 1 的范围内。

from sklearn.preprocessing import MinMaxScaler  # 从 sklearn.preprocessing 模块中导入 MinMaxScaler 类,用于数据归一化values = data['Weighted Price'].values.reshape(-1, 1)  # 从数据集中提取 "Weighted Price" 列的值,并将其重塑为列向量
values = values.astype('float32')  # 将提取的值转换为浮点数类型
scaler = MinMaxScaler(feature_range=(0, 1))  # 创建一个 MinMaxScaler 对象,将数据归一化到 0 到 1 的范围内
scaled = scaler.fit_transform(values)  # 使用 MinMaxScaler 对数据进行归一化处理
划分训练集和测试集

代码总结
这段代码的主要目的是将归一化后的数据集划分为训练集和测试集,其中 70% 的数据用于训练,30% 的数据用于测试。

train_size = int(len(scaled) * 0.7)  # 计算训练集的大小,占数据集的 70%
test_size = len(scaled) - train_size  # 计算测试集的大小,占数据集的 30%
train, test = scaled[0:train_size, :], scaled[train_size:len(scaled), :]  # 将数据集划分为训练集和测试集
print(len(train), len(test))  # 打印训练集和测试集的长度

在这里插入图片描述

创建具有回溯窗口的数据集

代码总结
这段代码的主要目的是创建一个函数 create_dataset,该函数生成具有指定回溯窗口的数据集,并将其用于生成训练和测试数据集。

def create_dataset(dataset, look_back=1):dataX, dataY = [], []  # 初始化数据集的输入和输出列表for i in range(len(dataset) - look_back):a = dataset[i:(i + look_back), 0]  # 获取回溯窗口内的数据dataX.append(a)  # 将回溯窗口内的数据添加到输入列表dataY.append(dataset[i + look_back, 0])  # 将下一个时间点的数据添加到输出列表print(len(dataY))  # 打印输出数据集的长度return np.array(dataX), np.array(dataY)  # 返回输入和输出数据集,转换为 NumPy 数组look_back = 1  # 设置回溯窗口的大小为 1
trainX, trainY = create_dataset(train, look_back)  # 使用训练集生成带有回溯窗口的训练数据集
testX, testY = create_dataset(test, look_back)  # 使用测试集生成带有回溯窗口的测试数据集

在这里插入图片描述

重塑 X 以适应模型训练

代码总结
这段代码的主要目的是将训练和测试数据集中的输入数据 trainXtestX 重塑为适合 LSTM 模型输入的形状。

trainX = np.reshape(trainX, (trainX.shape[0], 1, trainX.shape[1]))  # 将 trainX 重塑为 [样本数, 时间步数, 特征数] 的形状
testX = np.reshape(testX, (testX.shape[0], 1, testX.shape[1]))  # 将 testX 重塑为 [样本数, 时间步数, 特征数] 的形状
运行 LSTM 模型

代码总结
这段代码的主要目的是构建并训练一个 LSTM 模型,使用训练数据集进行 300 个周期的训练,并在测试数据集上进行验证。

model = Sequential()  # 创建一个顺序模型
model.add(LSTM(100, input_shape=(trainX.shape[1], trainX.shape[2])))  # 添加一个 LSTM 层,设置 100 个神经元,输入形状为 [时间步数, 特征数]
model.add(Dense(1))  # 添加一个全连接层,输出维度为 1
model.compile(loss='mae', optimizer='adam')  # 编译模型,使用均绝对误差(MAE)作为损失函数,Adam 优化器
history = model.fit(trainX, trainY, epochs=300, batch_size=100, validation_data=(testX, testY), verbose=0, shuffle=False)  # 训练模型,训练 300 个周期,每批 100 个样本,使用测试数据集进行验证
绘制训练和验证损失曲线

代码总结
这段代码的主要目的是绘制训练和验证过程中的损失曲线,以便观察模型的训练效果。

pyplot.plot(history.history['loss'], label='train')  # 绘制训练损失曲线,并添加标签 "train"
pyplot.plot(history.history['val_loss'], label='test')  # 绘制验证损失曲线,并添加标签 "test"
pyplot.legend()  # 添加图例
pyplot.show()  # 显示图表
使用测试数据进行预测并绘制折线图

代码总结
这段代码的主要目的是使用训练好的 LSTM 模型对测试数据进行预测,并绘制预测值与真实值的折线图。

yhat = model.predict(testX)  # 使用训练好的模型对测试数据进行预测
pyplot.plot(yhat, label='predict')  # 绘制预测值折线图,并添加标签 "predict"
pyplot.plot(testY, label='true')  # 绘制真实值折线图,并添加标签 "true"
pyplot.legend()  # 添加图例
pyplot.show()  # 显示图表

在这里插入图片描述

将预测值和真实值反归一化为原始值

代码总结
这段代码的主要目的是将预测值和真实值从归一化范围反归一化为原始值,并计算 RMSE。

yhat_inverse = scaler.inverse_transform(yhat.reshape(-1, 1))  # 将预测值反归一化为原始值
testY_inverse = scaler.inverse_transform(testY.reshape(-1, 1))  # 将真实值反归一化为原始值rmse = sqrt(mean_squared_error(testY_inverse, yhat_inverse))  # 计算预测值和真实值之间的均方根误差(RMSE)
print('Test RMSE: %.3f' % rmse)  # 打印测试 RMSE

在这里插入图片描述

绘制以美元为单位的折线图

代码总结
这段代码的主要目的是绘制预测值和真实值的折线图,Y 轴以美元为单位。

pyplot.plot(yhat_inverse, label='predict')  # 绘制预测值折线图,并添加标签 "predict"
pyplot.plot(testY_inverse, label='actual', alpha=0.5)  # 绘制真实值折线图,并添加标签 "actual",透明度为 0.5
pyplot.legend()  # 添加图例
pyplot.show()  # 显示图表
将 X 转换为日期

代码总结
这段代码的主要目的是将测试数据集的索引转换为日期。

predictDates = data.tail(len(testX)).index  # 获取测试数据集对应的日期索引
重塑测试数据和预测数据以适应 Plotly 绘图

代码总结
这段代码的主要目的是将反归一化后的测试数据和预测数据重塑为适合 Plotly 绘图的形状。

testY_reshape = testY_inverse.reshape(len(testY_inverse))  # 将真实值重塑为一维数组
yhat_reshape = yhat_inverse.reshape(len(yhat_inverse))  # 将预测值重塑为一维数组
使用 Plotly 绘制预测值和真实值的折线图

代码总结
这段代码的主要目的是使用 Plotly 绘制预测值和真实值的折线图,X 轴为日期,Y 轴为美元价格。

actual_chart = go.Scatter(x=predictDates, y=testY_reshape, name='Actual Price')  # 创建一个折线图数据对象,x 轴为日期,y 轴为真实值,图例名称为 "Actual Price"
predict_chart = go.Scatter(x=predictDates, y=yhat_reshape, name='Predict Price')  # 创建一个折线图数据对象,x 轴为日期,y 轴为预测值,图例名称为 "Predict Price"
py.iplot([predict_chart, actual_chart])  # 在 Jupyter Notebook 中显示折线图

使用额外特征进行模型训练

使用加权价格以及其他特征来训练 LSTM 模型。首先,找到特征与加权价格之间的相关性。通过绘制热力图,可以观察到交易量(Volume)与加权价格之间存在相关性,而开盘价(Open)、最高价(High)、最低价(Low)和收盘价(Close)则直接与加权价格相关。然后,创建一个函数 series_to_supervised 将数据序列转换为监督学习问题。接下来,提取所有相关特征的值,并将其归一化到 0 到 1 的范围内。将数据集转换为监督学习问题,并删除不必要的列。将数据集划分为 70% 的训练集和 30% 的测试集。训练 LSTM 模型 300 个周期,并绘制每个周期的损失曲线。使用测试数据进行预测,并绘制预测值与真实值的折线图。最后,将预测值和真实值反归一化为原始值,并计算 RMSE。绘制包含真实价格、单特征预测价格和多特征预测价格的折线图。结果显示,使用多特征的 LSTM 模型比使用单特征的 LSTM 模型更加准确。

找到特征与加权价格之间的相关性

代码总结
这段代码的主要目的是绘制数据集特征之间的相关性热力图,观察特征与加权价格之间的相关性。

import seaborn as sns  # 导入 seaborn 模块,用于绘制热力图# 绘制数据集特征之间的相关性热力图
sns.heatmap(data.corr(), annot=True, cmap='RdYlGn', linewidths=0.1, vmin=0)  # 使用 data.corr() 计算特征之间的相关性矩阵,并绘制热力图
# annot=True 表示在格子中显示相关性数值
# cmap='RdYlGn' 设置颜色主题
# linewidths=0.1 设置格子间的线条宽度
# vmin=0 设置热力图的最小值为 0# 观察:交易量(Volume)与加权价格(Weighted Price)之间存在相关性
# 开盘价(Open)、最高价(High)、最低价(Low)和收盘价(Close)直接与加权价格相关
函数 series_to_supervised 用于将数据序列转换为监督学习问题

代码总结
这段代码的主要目的是定义一个函数 series_to_supervised,将时间序列数据转换为监督学习问题,以便用于 LSTM 模型的训练。

def series_to_supervised(data, n_in=1, n_out=1, dropnan=True):n_vars = 1 if type(data) is list else data.shape[1]  # 确定特征的数量df = pd.DataFrame(data)  # 将数据转换为 DataFramecols, names = list(), list()  # 初始化列和列名列表# 输入序列(t-n, ..., t-1)for i in range(n_in, 0, -1):cols.append(df.shift(i))  # 将数据向后移 i 个时间步names += [('var%d(t-%d)' % (j+1, i)) for j in range(n_vars)]  # 生成列名# 预测序列(t, t+1, ..., t+n)for i in range(0, n_out):cols.append(df.shift(-i))  # 将数据向前移 i 个时间步if i == 0:names += [('var%d(t)' % (j+1)) for j in range(n_vars)]  # 生成当前时间步的列名else:names += [('var%d(t+%d)' % (j+1, i)) for j in range(n_vars)]  # 生成未来时间步的列名# 合并所有列agg = pd.concat(cols, axis=1)  # 按列合并所有数据agg.columns = names  # 设置列名# 删除包含 NaN 值的行if dropnan:agg.dropna(inplace=True)  # 删除包含 NaN 值的行return agg  # 返回转换后的数据集
获取所有相关特征的值

代码总结
这段代码的主要目的是从数据集中提取加权价格、交易量(BTC)和交易量(货币单位)的值,并将其转换为浮点数类型。

values = data[['Weighted Price'] + ['Volume (BTC)'] + ['Volume (Currency)']].values  # 从数据集中提取 "Weighted Price"、"Volume (BTC)" 和 "Volume (Currency)" 列的值
values = values.astype('float32')  # 将提取的值转换为浮点数类型
归一化特征值

代码总结
这段代码的主要目的是使用 MinMaxScaler 将提取的特征值归一化到 0 到 1 的范围内。

scaler = MinMaxScaler(feature_range=(0, 1))  # 创建一个 MinMaxScaler 对象,将数据归一化到 0 到 1 的范围内
scaled = scaler.fit_transform(values)  # 使用 MinMaxScaler 对数据进行归一化处理
将数据转换为监督学习问题

代码总结
这段代码的主要目的是将归一化后的数据转换为监督学习问题,并删除不必要的列。

reframed = series_to_supervised(scaled, 1, 1)  # 将归一化后的数据转换为监督学习问题,回溯窗口为 1,预测窗口为 1
reframed.head()  # 显示转换后的数据集的前 5 行# 删除不必要的列
reframed.drop(reframed.columns[[4, 5]], axis=1, inplace=True)  # 删除第 4 和第 5 列
print(reframed.head())  # 打印删除列后的数据集前 5 行

在这里插入图片描述
在这里插入图片描述

划分训练集和测试集

代码总结
这段代码的主要目的是将数据集划分为 70% 的训练集和 30% 的测试集,并将输入和输出数据分开。

values = reframed.values  # 获取转换后的数据集的值
n_train_hours = int(len(values) * 0.7)  # 计算训练集的大小,占数据集的 70%
train = values[:n_train_hours, :]  # 划分训练集
test = values[n_train_hours:, :]  # 划分测试集# 将训练集和测试集的数据分为输入和输出
train_X, train_y = train[:, :-1], train[:, -1]  # 训练集的输入和输出
test_X, test_y = test[:, :-1], test[:, -1]  # 测试集的输入和输出# 重塑输入数据,使其适应 LSTM 模型的输入形状 [样本数, 时间步数, 特征数]
train_X = train_X.reshape((train_X.shape[0], 1, train_X.shape[1]))  # 重塑训练集的输入数据
test_X = test_X.reshape((test_X.shape[0], 1, test_X.shape[1]))  # 重塑测试集的输入数据print(train_X.shape, train_y.shape, test_X.shape, test_y.shape)  # 打印训练集和测试集的形状

在这里插入图片描述

训练 LSTM 模型

代码总结
这段代码的主要目的是构建并训练一个 LSTM 模型,使用训练数据集进行 300 个周期的训练,并在测试数据集上进行验证。

from keras.models import Sequential  # 从 keras.models 模块中导入 Sequential 类
from keras.layers import LSTM, Dense  # 从 keras.layers 模块中导入 LSTM 和 Dense 层multi_model = Sequential()  # 创建一个顺序模型
multi_model.add(LSTM(100, input_shape=(train_X.shape[1], train_X.shape[2])))  # 添加一个 LSTM 层,设置 100 个神经元,输入形状为 [时间步数, 特征数]
multi_model.add(Dense(1))  # 添加一个全连接层,输出维度为 1
multi_model.compile(loss='mae', optimizer='adam')  # 编译模型,使用均绝对误差(MAE)作为损失函数,Adam 优化器# 训练模型
multi_history = multi_model.fit(train_X, train_y, epochs=300, batch_size=100, validation_data=(test_X, test_y), verbose=0, shuffle=False)  # 训练模型 300 个周期,每批 100 个样本,使用测试数据集进行验证
绘制训练和验证损失曲线

代码总结
这段代码的主要目的是绘制训练和验证过程中的损失曲线,以便观察模型的训练效果。

import matplotlib.pyplot as pyplot  # 导入 matplotlib.pyplot 模块,用于绘制图表pyplot.plot(multi_history.history['loss'], label='multi_train')  # 绘制训练损失曲线,并添加标签 "multi_train"
pyplot.plot(multi_history.history['val_loss'], label='multi_test')  # 绘制验证损失曲线,并添加标签 "multi_test"
pyplot.legend()  # 添加图例
pyplot.show()  # 显示图表

在这里插入图片描述

使用测试数据进行预测并绘制折线图

代码总结
这段代码的主要目的是使用训练好的 LSTM 模型对测试数据进行预测,并绘制预测值与真实值的折线图。

yhat = multi_model.predict(test_X)  # 使用训练好的模型对测试数据进行预测
pyplot.plot(yhat, label='predict')  # 绘制预测值折线图,并添加标签 "predict"
pyplot.plot(test_y, label='true')  # 绘制真实值折线图,并添加标签 "true"
pyplot.legend()  # 添加图例
pyplot.show()  # 显示图表
将预测值和真实值反归一化为原始值

代码总结
这段代码的主要目的是将预测值和真实值从归一化范围反归一化为原始值,并计算 RMSE。

test_X = test_X.reshape((test_X.shape[0], test_X.shape[2]))  # 重塑测试集的输入数据,使其恢复为二维数组# 反归一化预测值
inv_yhat = np.concatenate((yhat, test_X[:, 1:]), axis=1)  # 将预测值与测试集的其他特征值拼接
inv_yhat = scaler.inverse_transform(inv_yhat)  # 反归一化拼接后的数据
inv_yhat = inv_yhat[:, 0]  # 提取反归一化后的预测值# 反归一化真实值
test_y = test_y.reshape((len(test_y), 1))  # 将真实值重塑为二维数组
inv_y = np.concatenate((test_y, test_X[:, 1:]), axis=1)  # 将真实值与测试集的其他特征值拼接
inv_y = scaler.inverse_transform(inv_y)  # 反归一化拼接后的数据
inv_y = inv_y[:, 0]  # 提取反归一化后的真实值rmse = sqrt(mean_squared_error(inv_y, inv_yhat))  # 计算预测值和真实值之间的均方根误差(RMSE)
print('Test RMSE: %.3f' % rmse)  # 打印测试 RMSE

在这里插入图片描述

绘制包含真实价格、单特征预测价格和多特征预测价格的折线图

代码总结
这段代码的主要目的是绘制包含真实价格、单特征预测价格和多特征预测价格的折线图,X 轴为日期,Y 轴为美元价格。

import plotly.graph_objs as go  # 从 plotly.graph_objs 模块中导入 Scatter 类actual_chart = go.Scatter(x=predictDates, y=inv_y, name='Actual Price')  # 创建一个折线图数据对象,x 轴为日期,y 轴为真实值,图例名称为 "Actual Price"
multi_predict_chart = go.Scatter(x=predictDates, y=inv_yhat, name='Multi Predict Price')  # 创建一个折线图数据对象,x 轴为日期,y 轴为多特征预测值,图例名称为 "Multi Predict Price"
predict_chart = go.Scatter(x=predictDates, y=yhat_reshape, name='Predict Price')  # 创建一个折线图数据对象,x 轴为日期,y 轴为单特征预测值,图例名称为 "Predict Price"py.iplot([predict_chart, multi_predict_chart, actual_chart])  # 在 Jupyter Notebook 中显示折线图

结论

  • LSTM 仅使用加权价格特征的 RMSE 为 159.194
  • LSTM 使用交易量(BTC)、交易量(货币单位)和加权价格特征的 RMSE 为 96.184
  • 多特征的 LSTM 模型显示了更准确的结果,如上图所示
整体代码总结

链接: 【机器学习实战中阶】比特币价格预测器 源代码与数据集

这段代码的目的是读取一个包含比特币价格的数据集,并对其进行基本的信息查看。然后,基于数据集中的加权价格绘制折线图,以便直观地查看价格趋势。接下来,代码将加权价格中的 0 值替换为 NaN,并使用前向填充方法(ffill)来填充这些 NaN 值,以避免数据中的 0 值对模型训练产生影响。最后,再次绘制折线图,显示填充后的数据,确保数据处理的效果。

  1. 读取数据集

    • 使用 pd.read_csv 函数读取 CSV 文件,并将 “Date” 列设置为索引。
    • 使用 data.info() 查看数据集的基本信息。
    • 使用 data.head()data.tail() 分别显示数据集的前 5 行和最后 5 行。
  2. 绘制初始折线图

    • 使用 Plotly 的 go.Scatter 创建一个折线图数据对象,x 轴为日期,y 轴为加权价格。
    • 使用 py.iplot 在 Jupyter Notebook 中显示折线图。
  3. 数据处理

    • 使用 replace 方法将加权价格中的 0 值替换为 NaN。
    • 使用 fillna 方法的 ffill 参数(前向填充)来填充 NaN 值。
  4. 绘制处理后的折线图

    • 再次使用 go.Scatter 创建一个折线图数据对象,x 轴为日期,y 轴为处理后的加权价格。
    • 使用 py.iplot 在 Jupyter Notebook 中显示处理后的折线图。

在这里插入图片描述

在这里插入图片描述
比特币价格预测(轻量级CSV)关于数据集
致谢
这些数据来自CoinMarketCap,并且可以免费使用该数据。
https://coinmarketcap.com/

相关文章:

【机器学习实战中阶】比特币价格预测

比特币价格预测项目介绍 比特币价格预测项目是一个非常有实用价值的机器学习项目。随着区块链技术的快速发展,越来越多的数字货币如雨后春笋般涌现,尤其是比特币作为最早的加密货币,其价格波动备受全球投资者和研究者的关注。本项目的目标是…...

【JVM-9】Java性能调优利器:jmap工具使用指南与应用案例

在Java应用程序的性能调优和故障排查中,jmap(Java Memory Map)是一个不可或缺的工具。它可以帮助开发者分析Java堆内存的使用情况,生成堆转储文件(Heap Dump),并查看内存中的对象分布。无论是内…...

使用vscode在本地和远程服务器端运行和调试Python程序的方法总结

1 官网下载 下载网址:https://code.visualstudio.com/Download 如下图所示,可以分别下载Windows,Linux,macOS版本 历史版本下载链接: https://code.visualstudio.com/updates 2 安装Python扩展工具 打开 VS Code,安装 Microsoft 提供的官…...

AI 编程工具—Cursor 对话模式详解 Chat、Composer 与 Normal/Agent 模式

Cursor AI 对话模式详解:Chat、Composer 与 Normal/Agent 模式 一、简介 Cursor 是一个强大的 AI 辅助编程工具,它提供了多种对话模式来满足不同的开发需求。主要包括: Chat 模式:直接对话交互Composer 模式:结构化编程助手Normal/Agent 模式:不同的 AI 响应策略打开Ch…...

【MySQL】数据库基础知识

欢迎拜访:雾里看山-CSDN博客 本篇主题:【MySQL】数据库基础知识 发布时间:2025.1.21 隶属专栏:MySQL 目录 什么是数据库为什么要有数据库数据库的概念 主流数据库mysql的安装mysql登录使用一下mysql显示数据库内容创建一个数据库创…...

ChatGPT开发教程指南

ChatGPT开发教程指南 一、ChatGPT 概述二、开发环境搭建(一)硬件要求(二)软件要求 三、开发流程(一)数据处理(二)模型选择与训练(三)接口开发 四、示例代码 随…...

OpenEuler学习笔记(四):OpenEuler与CentOS的区别在那里?

OpenEuler与CentOS的对比 一、基本信息 起源与背景: OpenEuler:由华为发起,后捐赠给开放原子开源基金会,旨在构建一个开放、多元化的云计算和边缘计算平台,以满足华为及其他企业的硬件和软件需求。CentOS:…...

spring cloud如何实现负载均衡

在Spring Cloud中,实际上并没有直接支持lb:\\这样的URL前缀来自动解析为负载均衡的服务地址。lb:\\这样的表示可能是在某些特定框架、文档或示例中自定义的,但它并不是Spring Cloud官方API或规范的一部分。 Spring Cloud实现负载均衡的方式通常依赖于服…...

LeetCode:37. 解数独

跟着carl学算法,本系列博客仅做个人记录,建议大家都去看carl本人的博客,写的真的很好的! 代码随想录 LeetCode:37. 解数独 编写一个程序,通过填充空格来解决数独问题。 数独的解法需 遵循如下规则&#xff…...

如何在idea中搭建SpringBoot项目

如何在idea中快速搭建SpringBoot项目 目录 如何在idea中快速搭建SpringBoot项目前言一、环境准备:搭建前的精心布局 1.下载jdk (1)安装JDK:(2)运行安装程序:(3)设置安装…...

STM32补充——FLASH

目录 1.内部FLASH构成(F1) 2.FLASH读写过程(F1) 2.1内存的读取 2.2闪存的写入 2.3FLASH接口寄存器(写入 & 擦除相关) 3.FLASH相关HAL库函数简介(F1/F4/F7/H7) 4.编程实战 …...

ASP.NET Core 中的 JWT 鉴权实现

在当今的软件开发中,安全性和用户认证是至关重要的方面。JSON Web Token(JWT)作为一种流行的身份验证机制,因其简洁性和无状态特性而被广泛应用于各种应用中,尤其是在 ASP.NET Core 项目里。本文将详细介绍如何在 ASP.…...

Docker配置国内镜像源

访问docker hub需要科学上网 在 Docker 中配置镜像地址(即镜像加速器)可以显著提升拉取镜像的速度,尤其是在国内访问 Docker Hub 时。以下是详细的配置方法: 1. 配置镜像加速器 Docker 支持通过修改配置文件来添加镜像加速器地址…...

qiankun+vite+vue3

基座与子应用代码示例 本示例中,基座为Vue3,子应用也是Vue3,由于qiankun不支持Vite构建的项目,这里还要引入 vite-plugin-qiankun 插件 基座(主应用) 加载qiankun依赖 npm i qiankun -S qiankun配置(src/qiankun) src/qiankun/config.ts export default {subApp…...

如何使用AI工具cursor(内置ChatGPT 4o+claude-3.5)

⚠️温馨提示: 禁止商业用途,请支持正版,充值使用,尊重知识产权! 免责声明: 1、本教程仅用于学习和研究使用,不得用于商业或非法行为。 2、请遵守Cursor的服务条款以及相关法律法规。 3、本…...

Linux内核编程(二十一)USB驱动开发-键盘驱动

一、驱动类型 USB 驱动开发主要分为两种:主机侧的驱动程序和设备侧的驱动程序。一般我们编写的都是主机侧的USB驱动程序。 主机侧驱动程序用于控制插入到主机中的 USB 设备,而设备侧驱动程序则负责控制 USB 设备如何与主机通信。由于设备侧驱动程序通常与…...

vue3+ts watch 整理

watch() 一共可以接受三个参数,侦听数据源、回调函数和配置选项 作用:监视数据的变化(和Vue2中的watch作用一致) 特点:Vue3中的watch只能监视以下四种数据: ref定义的数据。 reactive定义的数据。 函数返…...

2025年最新深度学习环境搭建:Win11+ cuDNN + CUDA + Pytorch +深度学习环境配置保姆级教程

本文目录 一、查看驱动版本1.1 查看显卡驱动1.2 显卡驱动和CUDA对应版本1.3 Pytorch和Python对应的版本1.4 Pytorch和CUDA对应的版本 二、安装CUDA三、安装cuDANN四、安装pytorch五、验证是否安装成功 一、查看驱动版本 1.1 查看显卡驱动 输入命令nvidia-smi可以查看对应的驱…...

USART_串口通讯轮询案例(HAL库实现)

引言 前面讲述的串口通讯案例是使用寄存器方式实现的,有利于深入理解串口通讯底层原理,但其开发效率较低;对此,我们这里再讲基于HAL库实现的串口通讯轮询案例,实现高效开发。当然,本次案例需求仍然和前面寄…...

CAN 网络介绍

背景 在T-Box 产品开发过程中,我们离不开CAN总线,因为CAN总线为我们提供了车身的相关数据,比如,车速、油耗、温度等。用于上报TSP平台,进行国标认证;也帮助我们进行车身控制,比如车门解锁/闭锁…...

pytorch 多机多卡训练方法

在深度学习训练中,使用多机多卡(多台机器和多块 GPU)可以显著加速模型训练过程。 PyTorch 提供了多种方法来实现多机多卡训练,以下是一些常用的方法和步骤: 1. 使用 torch.distributed 包 PyTorch 的 torch.distribut…...

【智能控制】年末总结,模糊控制,神经网络控制,专家控制,遗传算法

关注作者了解更多 我的其他CSDN专栏 毕业设计 求职面试 大学英语 过程控制系统 工程测试技术 虚拟仪器技术 可编程控制器 工业现场总线 数字图像处理 智能控制 传感器技术 嵌入式系统 复变函数与积分变换 单片机原理 线性代数 大学物理 热工与工程流体力学 …...

Linux系统 C/C++编程基础——使用make工具和Makefile实现自动编译

ℹ️大家好,我是练小杰,今天周二了,距离除夕只有6天了,新的一年就快到了😆 本文是有关Linux C/C编程的make和Makefile实现自动编译相关知识点,后续会不断添加相关内容 ~~ 回顾:【Emacs编辑器、G…...

kafka学习笔记7 性能测试 —— 筑梦之路

kafka 不同的参数配置对 kafka 性能都会造成影响,通常情况下集群性能受分区、磁盘和线程等影响因素,因此需要进行性能测试,找出集群性能瓶颈和最佳参数。 # 生产者和消费者的性能测试工具 kafka-producer-perf-test.sh kafka-consumer-perf-t…...

C#与AI的共同发展

C#与人工智能(AI)的共同发展反映了编程语言随着技术进步而演变,以适应新的挑战和需要。自2000年微软推出C#以来,这门语言经历了多次迭代,不仅成为了.NET平台的主要编程语言之一,还逐渐成为构建各种类型应用程序的强大工具。随着时…...

multus使用教程

操作步骤如下: 1.在vmware vsphere上配置所有主机使用的端口组安全项 Forged transmits 设置为: Accept Promiscuous Mode 设置为:Accept Promiscuous Mode(混杂模式)和Forged Transmits(伪传输&#xff09…...

用JAVA写算法之输入输出篇

本系列适合原来用C语言或其他语言写算法,但是因为找工作或比赛的原因改用JAVA语言写算法的同学。当然也同样适合初学算法,想用JAVA来写算法题的同学。 常规方法:使用Scanner类和System.out 这种方法适用于leetcode,以及一些面试手…...

场馆预定平台高并发时间段预定实现V2

🎯 本文档介绍了场馆预订系统接口V2的设计与实现,旨在解决V1版本中库存数据不一致及性能瓶颈的问题。通过引入令牌机制确保缓存和数据库库存的最终一致性,避免因服务器故障导致的库存错误占用问题。同时,采用消息队列异步处理库存…...

(1)STM32 USB设备开发-基础知识

开篇感谢: 【经验分享】STM32 USB相关知识扫盲 - STM32团队 ST意法半导体中文论坛 单片机学习记录_桃成蹊2.0的博客-CSDN博客 USB_不吃鱼的猫丿的博客-CSDN博客 1、USB鼠标_哔哩哔哩_bilibili usb_冰糖葫的博客-CSDN博客 USB_lqonlylove的博客-CSDN博客 USB …...

Spring Boot 整合 ShedLock 处理定时任务重复执行的问题

🌷 古之立大事者,不惟有超世之才,亦必有坚忍不拔之志 🎐 个人CSND主页——Micro麦可乐的博客 🐥《Docker实操教程》专栏以最新的Centos版本为基础进行Docker实操教程,入门到实战 🌺《RabbitMQ》…...

缓存之美:万文详解 Caffeine 实现原理(上)

由于社区最大字数限制,本文章将分为两篇,第二篇文章为缓存之美:万文详解 Caffeine 实现原理(下) 大家好,我是 方圆。文章将采用“总-分-总”的结构对配置固定大小元素驱逐策略的 Caffeine 缓存进行介绍&…...

PHP语言的网络编程

PHP语言的网络编程 网络编程是现代软件开发中不可或缺的一部分,尤其是在日益发展的互联网时代。PHP(Hypertext Preprocessor)是一种广泛使用的开源脚本语言,专门用于Web开发。它的灵活性、易用性以及强大的社区支持使得PHP在网络…...

【技巧】优雅的使用 pnpm+Monorepo 单体仓库构建一个高效、灵活的多项目架构

单体仓库(Monorepo)搭建指南:从零开始 单体仓库(Monorepo)是一种将多个相关项目集中管理在一个仓库中的开发模式。它可以帮助开发者共享代码、统一配置,并简化依赖管理。本文将通过实际代码示例&#xff0…...

算法项目实时推流

1、搭建流媒体服务器 下载mediamtx 2、视频流直推 ffmpeg -stream_loop -1 -i DJI_20250109112715_0002_W.MP4 -r 30 -c:v libx264 -preset ultrafast -f flv rtmp://192.168.100.20:1935/live/test_chengdu1 3、硬件加速 如果硬件支持,可以使用硬件加速编码器&am…...

软件测试—— 接口测试(HTTP和HTTPS)

软件测试—— 接口测试(HTTP和HTTPS) HTTP请求方法GET特点使用场景URL结构URL组成部分URL编码总结 POST特点使用场景请求结构示例 请求标头和响应标头请求标头(Request Headers)示例请求标头 响应标头(Response Header…...

PCL K4PCS算法实现点云粗配准【2025最新版】

目录 一、算法原理1、算法概述2、算法流程3、参考文献二、 代码实现1、原始版本2、2024新版三、 结果展示本文由CSDN点云侠原创,原文链接,首发于:2020年4月27日。如果你不是在点云侠的博客中看到该文章,那么此处便是不要脸的抄袭狗。 博客长期更新,本文最近一次更新时间为…...

Docker 学习总结(85)—— docker cp 使用总结

前言 在现代软件开发中,Docker 已成为一种流行的容器化技术。无论是在开发、测试还是生产环境中,管理容器内的文件都是一项常见且重要的任务。本文将详细介绍如何使用 docker cp 命令在 Docker 容器与宿主机之间拷贝文件和目录,并结合一些实际使用场景,帮助您更高效地管理…...

《FMambaIR:一种基于混合状态空间模型和频域的方法用于图像恢复》学习笔记

paper:(PDF) FMambaIR: A Hybrid State Space Model and Frequency Domain for Image Restoration 目录 摘要 一、引言 二、相关工作 1、图像恢复 2、频率学习 3、状态空间模型(SSM) 三、框架 1、基本知识 2、整体框架 3、F-Mamba…...

PyQt5 超详细入门级教程上篇

PyQt5 超详细入门级教程 上篇:1-3部分:PyQt5基础与常用控件 第1部分:初识 PyQt5 和安装 1.1 什么是 PyQt5? PyQt5 是 Python 的图形用户界面 (GUI) 框架,它基于强大的 Qt 库。Qt 是一个跨平台的 C 框架,用…...

通信协议—WebSocket

一、WebSocket编程概念 1.1 什么是WebSocket WebSocket 是一种全双工通信协议,允许在客户端(通常是浏览器)和服务器之间建立持久连接,以实现实时的双向通信。它是 HTML5 标准的一部分,相比传统的 HTTP 请求&#xff…...

FFmpeg音视频采集

文章目录 音视频采集音频采集获取设备信息录制麦克风录制声卡 视频采集摄像机画面采集 音视频采集 DirectShow(简称DShow)是一个Windows平台上的流媒体框架,提供了高质量的多媒体流采集和回放功能,它支持多种多样的媒体文件格式&…...

【微机原理与接口技术】定时控制接口

文章目录 8253的引脚和工作方式内部结构和引脚工作方式方式0:计数结束中断方式1:可编程单稳脉冲方式2:周期性负脉冲输出方式3:方波发生器方式4:软件触发的单次负脉冲输出方式5:硬件触发的单次负脉冲输出各种…...

AG32 FPGA 的 Block RAM 资源:M9K 使用

1. 概述 AG32 FPGA 包含了 4 个 M9K 块,每个 M9K 块的容量为 8192 bits,总计为 4 个 M9K(4K bytes)。这使得 AG32 的内部存储非常适合嵌入式应用,能够有效地利用片上资源。 M9K 参数 参考自《AGRV2K_Rev2.0.pdf》。…...

第3天:阿里巴巴微服务解决方案概览

一、阿里巴巴微服务解决方案概述 阿里巴巴在微服务领域贡献了多个开源项目,形成了完整的微服务解决方案,广泛应用于分布式系统开发。其中,Spring Cloud Alibaba 是基于 Spring Cloud 构建的一站式微服务解决方案,集成了多个阿里巴…...

在Ubuntu上安装RabbitMQ教程

1、安装erlang 因为rabbitmq是基于erlang开发的,所以要安装rabbitmq,首先需要安装erlang运行环境 apt-get install erlang执行命令查是否安装成功:erl,疯狂 Ctrlc 就能退出命令行 2、安装rabbitmq 1、查看erlang与rabbitmq版本…...

WPF 引发类型为“System.Windows.Forms.AxHost+InvalidActiveXStateException”的异常 解决办法

本章讲述:引发类型为“System.Windows.Forms.AxHostInvalidActiveXStateException”的异常 解决办法。 这几天在做一个WPF功能时,因为引用了第三方的OCX控件,一般来说一个对象只要实例化就行了, 但是在引用这个控件时就报引发类型为“System.…...

Vue 3中导航守卫(Navigation Guard)结合Axios实现token认证机制

在Vue 3中,导航守卫(Navigation Guard)用于拦截路由的变化,可以在用户访问页面前进行检查。结合Axios进行token认证机制时,我们可以通过导航守卫在路由跳转时,检查用户的认证状态,确保用户有有效…...

代码随想录算法【Day28】

Day28 122.买卖股票的最佳时机 II 最终利润是可以分解的 假如第 0 天买入,第 3 天卖出,那么利润为:prices[3] - prices[0]。 相当于(prices[3] - prices[2]) (prices[2] - prices[1]) (prices[1] - prices[0])。 所以把利润分解为每天…...

【21】Word:德国旅游业务❗

目录 题目 NO1.2.3 NO4 NO5.6 NO7 NO8.9.10.11 题目 NO1.2.3 F12:另存为布局→页面设置→页边距:上下左右选中“德国主要城市”→开始→字体对话框→字体/字号→文本效果:段落对话框→对齐方式/字符间距/段落间距 NO4 布局→表对话框…...

基于 MDL 行情插件的中金所 L1 数据处理最佳实践

本文介绍了如何通过 DolphinDB 的 MDL 插件订阅并处理中金所 Level 1 实时数据。首先,文章简要介绍了 MDL 插件的功能和作用。它是基于 MDL 官方提供的行情数据服务 C SDK(即 TCP 版本 MDL )实现,提供了实时数据获取和处理的能力。…...