做股票预测系统这个选题,十个里至少有八个是冲着“大数据+Hadoop+深度学习”这个组合去的。这三个词放一起,分量确实够——大数据是底座,Hadoop解决分布式存储与分布式计算的骨架问题,深度学习作为预测引擎,一套组合下来,源码、论文、答辩PPT都能填得满满的。这篇文章我就基于这个题目的完整开发链路,把需求拆解、技术选型、数据采集、Hadoop生态落地、LSTM模型调参、系统联调、以及论文和答辩材料的打磨顺序串起来讲一遍,重点放在那些不是文档里能查到的决策逻辑和实际踩坑点。
这个选题适合两类人:一类是大数据专业或者计算机相关专业要做毕业设计的学生,另一类是打算用炒股数据练手、想跑通一套“数据采集—分布式存储—特征工程—模型训练—Web展示”全流程的开发者。无论你是哪个角色,只要把下面这些环节吃透,这套系统不只是能答辩,放到简历上也是一个完整可讲的项目。
1. 这个项目的真实定位与技术选型逻辑
1.1 从毕业设计视角拆解核心需求
很多人拿到这个题目就开始写代码,结果写到一半发现不知道自己在做什么。先冷静下来拆题:题目是“基于大数据+Hadoop+深度学习的股票预测系统”,关键词有三个,分别是大数据、Hadoop、深度学习。这意味着你的项目必须同时体现三件事:一是数据规模和处理链路要配得上“大数据”这个概念,需要有分布式存储或者至少分布式文件存储;二是要有实实在在的Hadoop生态组件参与工作,光写个MapReduce WordCount就是敷衍;三是预测环节必须用深度学习模型,而不是sklearn随便跑个线性回归糊弄。
从交付物角度,毕业设计通常要求源码、论文和答辩PPT。源码要能一键跑通,论文要结构完整且有自己的工作量,PPT要能在10分钟内把项目讲清楚。很多人的误区在于把代码写得很炫,但论文和PPT一塌糊涂,答辩被老师追着问就露馅了。所以这个项目从一开始就要有工程思维:先定架构,再写模块,边写边记录设计理由,最后这些理由就是论文里的“系统设计”章节。
从数据角度,股票历史行情数据天然适合做大数据链路,分钟级、日线级的K线数据量大、结构明确、带有时间属性,处理逻辑可解释性强。你不需要真的抓全球市场的数据,单是A股几千只股票几年的日线数据,已经足够让单机处理产生压力,Hadoop就有了用武之地。
1.2 大数据栈与深度学习栈的合理分工
这个项目里,Hadoop和大数据不是“装饰”,深度学习也不是累赘,两者的分工必须清晰:
- Hadoop生态负责历史数据的批量存储和预处理。原始行情数据从接口拉下来后,先落到HDFS,再用Hive或者MapReduce完成清洗、去重、缺失值填充,以及技术指标的计算。数据量大了以后,分布式存储和分布式计算的优势才体现出来。
- 深度学习部分负责预测。清洗后的数据从Hive导出为训练样本,喂给LSTM类的时间序列模型,得到预测结果。
- Web和可视化部分负责结果展示。后端封装预测接口,前端用可视化图表展示历史K线和未来预测曲线。
这个分工的好处是,每一层都有清晰的技术点,论文里每一章都有内容可写。更重要的是,它符合真实的工业处理流程:数据先入湖,再加工,再进入模型训练。答辩时老师问“为什么用Hadoop”,你可以从数据容量、计算效率、扩展性三个角度回答,而不是说“因为题目要求”。
1.3 选型背后的三个关键权衡
第一个权衡:Hadoop生态组件选哪些。完整的数据仓库方案通常要上Hive、Spark、Flink,但对一个毕业设计来说,适当做减法反而加分。我的建议是核心保留HDFS和Hive,MapReduce可以作为补充,如果有余力再加一个Spark SQL做特征计算的对比。Hive的优势在于可以用类SQL写清洗逻辑,论文里好交代,代码也容易维护。
第二个权衡:深度学习框架选TensorFlow还是PyTorch。两者都可以,主要看你熟悉哪个。我用TensorFlow的Keras接口比较多,因为代码简洁,LSTM这种模型几行就能搭出来。如果你后续想做更复杂的注意力机制,PyTorch的灵活性更好。这个选型不重要,重要的是你能把模型结构的每一层都讲清楚。
第三个权衡:预测目标到底是价格还是涨跌方向。好多人一上来就预测明天的收盘价,训练出来的模型误差率看起来不高,实际上只是学了一个“明天价格约等于今天价格”的复制函数,毫无意义。更学术化的做法是预测未来N日的趋势方向,或者预测收益率的变动。这里我建议做二分类或者多分类的涨跌预测,这样评估指标用准确率、F1-score更有说服力,也规避了“精确预测股价”这种答辩时容易被挑战的痛点。
2. Hadoop生态落地:从原始数据到特征宽表
2.1 集群准备与数据采集链路搭建
先说环境。完全分布式Hadoop集群需要至少3台机器,学生党没条件的直接用伪分布式模式也能跑通全流程,只是性能上没有对比性。我自己测试时用的是三台云主机,每台2核4G,操作系统用的CentOS 7,Hadoop版本选的3.x。内存不大,所以YARN的调度器和MapReduce的内存参数必须手动调小,不然任务一跑就OOM。
集群装好后测试管理界面是第一优先级。NameNode的50070端口页面、YARN ResourceManager的8088端口页面能正常打开,说明基础环境没问题。然后配置SSH免密登录,格式化NameNode,启动HDFS和YARN集群。这些步骤属于基本功,但很容易出幺蛾子,常见的是hostname配置不一致、端口被占用、防火墙没关。建议一步一步在文中记录命令,后面写论文的“系统环境搭建”可以直接用。
数据采集这块,推荐用Python写一个定时爬虫脚本。不要自己去解析网页,直接用开源行情接口,现在市面上很多免费的数据源,申请个token就能拉数据,日线行情完全够用。采集维度包括开盘价、最高价、最低价、收盘价、成交量、成交额,再加一个股票代码和交易日期。脚本跑完后自动生成CSV文件,每个文件按股票代码命名,比如stock_600000.csv(这里只是占位符,实际用你要预测的股票代码)。
import requests import pandas as pd # 这里换成你实际申请的开源行情接口 url = "https://example.api.com/market/kline" params = { "symbol": "your_symbol", "period": "daily", "start_date": "2018-01-01", "end_date": "2024-12-01", "token": "your_token_here", } resp = requests.get(url, params=params).json() df = pd.DataFrame(resp["data"]["items"]) df.columns = ["date", "open", "high", "low", "close", "volume", "amount"] df.to_csv("/data/stock_your_symbol.csv", index=False)采集脚本要注意两个问题:一是接口的访问频率限制,一次拉全量数据容易封token,最好循环分批拉取;二是时区和复权问题,股票数据有前复权后复权的区别,做模型训练时统一使用前复权数据,否则除权除息会造成价格跳变,影响模型。
2.2 HDFS存储与Hive清洗的实操细节
数据采集完成后,先把CSV文件传到HDFS。按日期或按股票代码建立目录层级,我建议采用“/stock/raw/采集日期/”这种分区式目录,为后面Hive分区表做准备。
hdfs dfs -mkdir -p /stock/raw/20241201 hdfs dfs -put /data/stock_your_symbol.csv /stock/raw/20241201/接着在Hive里建一张外部表,指向HDFS目录。外部表的优势是删除表不会删除HDFS数据,对实验性项目更安全。表结构按股票代码、交易日期、OHLCV字段设计,使用分区字段按采集日期分区,存储格式选择ORC列式存储,查询性能和压缩比都更好。
建表SQL大致如下:
CREATE EXTERNAL TABLE IF NOT EXISTS stock_daily ( symbol STRING, trade_date DATE, open DOUBLE, high DOUBLE, low DOUBLE, close DOUBLE, volume BIGINT, amount DOUBLE ) PARTITIONED BY (dt STRING) ROW FORMAT DELIMITED FIELDS TERMINATED BY ',' STORED AS ORC LOCATION '/stock/warehouse/daily'; -- 添加分区 ALTER TABLE stock_daily ADD PARTITION (dt='20241201');Hive的清洗逻辑主要处理三类问题:第一,过滤字段为空或者明显异常的数据,比如开盘价为负;第二,去重,同一个股票同一天可能有两条记录,用开窗函数按交易时间倒序排序取第一条;第三,填充缺失日期,股票交易停牌时没有记录,需要按交易时间序列补全,缺失的OHLCV字段用前一天的收盘价填充。
INSERT OVERWRITE TABLE stock_clean SELECT symbol, trade_date, open, high, low, close, volume, amount FROM ( SELECT *, ROW_NUMBER() OVER (PARTITION BY symbol, trade_date ORDER BY trade_date DESC) AS rn FROM stock_daily ) t WHERE t.rn = 1;数据清洗做完后,在Hive里把多只股票、多年数据整合成一张“特征宽表”。宽表里除了原始OHLCV,还要计算技术指标,比如5日均线、10日均线、RSI、MACD这些。技术指标的计算逻辑要写清楚,因为论文里要提。比如5日均线的计算,在Hive里可以用窗口函数直接做:
SELECT symbol, trade_date, close, AVG(close) OVER (PARTITION BY symbol ORDER BY trade_date ROWS BETWEEN 4 PRECEDING AND CURRENT ROW) AS ma5, AVG(close) OVER (PARTITION BY symbol ORDER BY trade_date ROWS BETWEEN 9 PRECEDING AND CURRENT ROW) AS ma10 FROM stock_clean;这里有个易踩的坑:窗口函数的排序字段trade_date必须是连续的交易日序列,如果中间因为停牌缺了数据,算出来的均线会有偏差。所以清洗阶段务必把缺失交易日补全,这也是为什么上面特意提到填充缺失日期。
2.3 特征工程:把行情数据变成模型能吃的样本
特征工程是整个项目里最容易提升论文含金量的环节。千万别只把原始OHLCV丢给深度学习模型就完事,那样输出几乎是“复制上一个交易日价格”。
我实际使用的特征分三类:原始行情特征、统计特征、技术指标特征。
原始行情特征就是open、high、low、close、volume、amount。统计特征包括过去5日、10日、20日的收益率均值、波动率、最高价与最低价的比例。技术指标特征包括MA5、MA10、MA20、RSI、MACD的DIF与DEA、布林带上下轨位置。这些特征加一起大约20个维度,对LSTM来说不算大,但预测效果明显比只用OHLCV好。
特征工程做完后,数据从Hive导出到本地文件系统,或者直接通过Hive的查询结果生成CSV供Python读取。如果数据量大,导出时需要分片,避免单文件过大导致后续读取卡顿。
hive -e "SELECT * FROM stock_feature WHERE dt='20241201'" > /data/feature_20241201.csv导出后的数据要在Python里做归一化。我的做法是使用MinMaxScaler把每个特征缩放到0到1之间。注意这里有一个特别关键的细节:归一化的scaler参数只能在训练集上拟合,再应用到验证集和测试集,绝对不能在整个数据集上先归一化再切分,否则会造成数据泄漏,测试指标会虚高,答辩时被专业老师一眼看穿。
3. 深度学习模型构建与调参实录
3.1 序列样本构建与时间窗口选择
LSTM处理的是序列数据,所以原始数据要改造成“滑动窗口”形式的样本。假设我们决定用过去60个交易日的特征预测未来1天的方向,那么第1个样本就是第1到第60天的数据作为输入,第61天的涨跌标签作为输出,然后窗口往后滑动一天生成第2个样本,依此类推。
代码实现大致是这样:
import numpy as np from sklearn.preprocessing import MinMaxScaler def build_sequences(data, feature_cols, target_col, window=60): X, y = [], [] for i in range(len(data) - window): X.append(data[feature_cols].iloc[i:i+window].values) y.append(data[target_col].iloc[i+window]) return np.array(X), np.array(y)时间窗口选多少不是拍脑袋定的。60个交易日大约对应3个月,能捕捉中短期趋势;120个交易日对应半年,更能反映中期趋势。窗口太长会引入过多噪声,增加计算负担;窗口太短则可能信息不足。我在实验里对比了30、60、90三个窗口,60的综合表现最好,论文里可以放一个窗口选择的对比实验。
训练数据的切分也要讲策略。不建议随机抽样切分,因为时间序列存在顺序依赖,必须按时间顺序切分。我的习惯是按时间比例切分,前70%做训练、15%做验证、15%做测试,确保测试集时间在训练集之后。这种切分方式模拟的是真实场景:用历史数据训练模型,预测未来。
3.2 LSTM网络结构的设计思路
LSTM网络结构不要一开始就堆很深的层,过度复杂的模型在小数据集上非常容易过拟合。我用的基准结构是输入层加两层LSTM,中间加Dropout,最后接一个Dense输出层。
如果做预测涨跌方向的二分类,模型结构和代码如下:
from tensorflow.keras.models import Sequential from tensorflow.keras.layers import LSTM, Dense, Dropout from tensorflow.keras.optimizers import Adam model = Sequential() model.add(LSTM(64, return_sequences=True, input_shape=(60, X.shape[2]))) model.add(Dropout(0.2)) model.add(LSTM(32)) model.add(Dropout(0.2)) model.add(Dense(16, activation="relu")) model.add(Dense(1, activation="sigmoid")) model.compile(optimizer=Adam(learning_rate=0.001), loss="binary_crossentropy", metrics=["accuracy", "AUC"])第一层LSTM设置return_sequences=True是为了向下一个LSTM层传递完整的序列信息,如果只有一层LSTM,不需要这么设置。units的取值64和32是我试过比较均衡的默认值,并不是越大越好。神经元越多,模型容量越大,但训练耗时和过拟合风险也同时上升。
Dropout是应对过拟合最有效的正则化手段,尤其是在金融序列这种信噪比很低的数据上。金融数据本身随机性很强,模型很容易去记噪声,Dropout能够强制网络学习更鲁棒的模式。我在多次实验中,加上Dropout之后验证集准确率大约能提升3到5个百分点。
3.3 训练策略、评估指标与回测可视化
训练过程的重点是设置合理的回调函数。EarlyStopping监控验证集loss,连续5个epoch不下降就停止,避免无效训练;ModelCheckpoint保存验证集表现最好的模型权重,防止训练后期因为过拟合把最优模型覆盖掉。
from tensorflow.keras.callbacks import EarlyStopping, ModelCheckpoint callbacks = [ EarlyStopping(monitor="val_loss", patience=5, restore_best_weights=True), ModelCheckpoint("best_model.h5", monitor="val_accuracy", save_best_only=True) ] history = model.fit( X_train, y_train, validation_data=(X_val, y_val), epochs=50, batch_size=128, callbacks=callbacks, verbose=1 )评估指标不要只看准确率。金融数据里涨跌样本分布往往不平衡,如果跌的样本占60%,模型只要全部预测跌,准确率也能有60%。所以这里要一起看精确率、召回率和F1-score,如果是回归预测就看RMSE和MAPE。
对于预测结果的可视化,推荐两个图:第一个是训练曲线图,横轴是epoch,纵轴是loss和accuracy,展示训练集和验证集的变化趋势;第二个是回测效果图,在测试集上把模型预测的涨跌方向与实际涨跌方向画在一起,直观展示模型在时间轴上的预测表现。这两张图写进论文里,实验分析章节就非常丰满。
我自己实验中一个比较直观的感受是:从测试集准确率看,模型在趋势明显的行情段表现更好,在震荡行情段预测能力接近随机。这一点也要提前写在论文的“结果分析”里,坦承模型的局限,反而比吹嘘准确率高更让答辩老师认可。
4. 从模型到完整系统:接口、页面与联调
4.1 预测服务封装与接口设计
模型训练完成后,不能只停留在Jupyter Notebook里,要封装成可调用的服务。我采用Flask搭建预测服务,提供一个POST接口,接收股票代码和时间窗口参数,返回预测结果。
接口设计遵循简单原则,核心逻辑如下:
from flask import Flask, request, jsonify import joblib import numpy as np from datetime import datetime app = Flask(__name__) model = load_model() scaler = joblib.load("scaler.pkl") @app.route("/predict", methods=["POST"]) def predict(): data = request.get_json() symbol = data.get("symbol") seq = data.get("sequence") # 前端传过来的最近N日特征序列 scaled_seq = scaler.transform(np.array(seq)) input_tensor = scaled_seq.reshape(1, window, n_features) pred = model.predict(input_tensor)[0][0] result = { "symbol": symbol, "prediction": float(pred), "confidence": float(pred if pred > 0.5 else 1 - pred), "timestamp": datetime.now().isoformat() } return jsonify(result) app.run(host="0.0.0.0", port=8080, debug=False)接口封装时要考虑两个问题:一是输入特征必须与训练时完全一致,包括特征顺序和归一化参数;二是预测结果要附带置信度或概率阈值,前端展示时用户可以知道这是高置信度预测还是低置信度预测。
这里有个容易把初学者坑到的地方:训练模型时用的scaler是保存在Python对象里的,模型服务和训练环境可能不在同一个机器,必须把scaler一起保存并加载,否则预测时数据没做同样尺度的缩放,输出结果必然不对。
4.2 前端可视化与交互逻辑
前端页面不必做复杂框架,一个单页HTML加ECharts图表足以满足答辩展示需求。页面布局分为三块:顶部是股票选择和参数设置区,中间是K线图与预测曲线图,底部是预测结果指标卡片。
K线图使用ECharts的candlestick系列,预测曲线可以使用line系列叠加在K线图之上。交互逻辑很简单:用户选择股票代码和预测天数,点击“预测”按钮,后端接口返回结果,前端把预测值画成虚线延长线。这样一个交互闭环就完成了。
前端调接口时要注意跨域问题。如果前端页面和后端服务不在同一端口,需要给Flask配置CORS,否则浏览器会拦截请求。可以在Flask中直接添加响应头解决:
@app.after_request def add_cors_headers(response): response.headers["Access-Control-Allow-Origin"] = "*" response.headers["Access-Control-Allow-Methods"] = "POST, GET, OPTIONS" response.headers["Access-Control-Allow-Headers"] = "Content-Type" return responseECharts这块是纯前端工作,需要你提前准备爬取的数据接口返回近期历史K线,因为前端页面只负责展示,不直接连数据库。可以再给后端加一个“/history”接口返回最近60个交易日的OHLCV数据。
4.3 定时任务与全流程串联
系统要体现“自动运行”的能力,不能每次手动跑脚本。用crontab配置两个定时任务:每天收盘后自动采集当日行情数据;每周或每两周自动重新训练一次模型。
定时任务的效果在演示环节很加分。你可以把系统挂在那里跑两天,答辩时展示数据库中每日新增的记录和模型更新日志,证明系统的完整性和可用性。
# 每天 17:30 拉取当日行情 30 17 * * 1-5 /usr/bin/python3 /opt/stock_project/scripts/collect_daily.py >> /opt/stock_project/logs/collect.log 2>&1 # 每周日凌晨 2:00 重新训练模型 0 2 * * 0 /usr/bin/python3 /opt/stock_project/scripts/train_model.py >> /opt/stock_project/logs/train.log 2>&1全流程串联完成后,建议写一个一键启动脚本,依次检查HDFS状态、启动数据采集、执行Hive清洗、导出特征、启动Flask服务。答辩现场环境复杂,一键启动能减少演示时的操作失误。
5. 论文写作与答辩资料的打磨要点
5.1 论文结构与“新意”怎么写
论文结构基本按照“摘要—绪论—相关技术—需求分析—系统设计—系统实现—实验分析—总结”的套路走,重点在于每一章必须填充“自己做的东西”,而不是复制概念介绍。
绪论里的国内外现状要写具体的代表工作,比如某团队提出了基于注意力机制的金融时间序列预测方法,某团队把图神经网络用到了股票关联关系建模上。写这些是为了引出自己的研究切入点,而不是简单罗列。
论文的核心新意可以围绕两点展开:一是基于Hadoop生态建设了一套可复用的股票数据仓库与特征计算流程,解决了数据处理和特征工程的一致性问题;二是在LSTM基础上引入了多维度特征融合,对比分析了带技术指标特征和不带技术指标特征的预测效果差异。这两点都属于“工程量+实验量”的落地创新,不夸张,但足够支撑一篇合格论文。
系统设计章节最好配一张系统架构图,分层展示数据采集层、分布式存储层、数据处理层、模型训练层、应用展示层。每个层的功能和组件写清楚。
5.2 答辩PPT的十页框架
答辩PPT切忌页数过多,10到12页足够,核心逻辑是“为什么做、怎么设计、怎么做、做得怎么样、有什么亮点”。
我的推荐框架如下:
- 封面页:题目、姓名、学号
- 目录页:栏目导航
- 背景与意义:选题的背景、要解决的问题
- 国内外现状:简述已有方法与本项目的差异
- 系统总体设计:架构图加各层职责说明
- 关键技术实现:Hadoop/Hive的数据处理、特征工程流程
- 深度学习模型设计:模型结构图、训练策略
- 实验结果分析:对比实验表格、可视化图表
- 系统演示:截图或者现场演示入口
- 总结与展望:研究结论、后续可以做的方向
每一页文字不宜过多,页面上放核心图表和关键结论,讲解时口头展开。特别是系统架构图和模型结构图,这两页是老师停留时间最长的部分,值得花心思画清晰。
5.3 高频答辩问题与应对话术
答辩环节老师最常问的问题我整理了一个列表,准备充分就能应对:
| 问题 | 参考回答思路 |
|---|---|
| 为什么用Hadoop,你的数据量单机也能处理? | 承认单机可以处理当前规模,但系统设计目标是可扩展的数据处理链路。随着股票数量和时间跨度增长,单机存储和计算都会成为瓶颈,HDFS提供了横向扩展能力,Hive提升了处理效率 |
| LSTM为什么能预测股票? | LSTM能记住序列中的长期依赖关系,相比RNN缓解了梯度消失问题。股票历史价格中存在一定的趋势性、周期性和惯性,LSTM可以从历史序列中提取这些模式 |
| 你的模型和普通机器学习模型相比优势在哪? | LSTM天然适合序列数据建模,支持变长输入和多维特征,不需要手动构造滞后特征。同时我在实验中加入了与XGBoost或随机森林的对比实验,从结果看LSTM在序列指标上更优 |
| 预测结果能用于真实交易吗? | 不能。金融市场受政策、消息面影响巨大,模型只作为学术研究方法验证。这也是目前学界普遍认识:价格预测的稳定性无法保证,研究方向正在向多因子模型和风险预测转移 |
| 数据泄漏怎么避免? | 归一化参数只在训练集上拟合,测试集数据不参与;时间序列按时间顺序切分;特征计算只用历史窗口数据,不引入未来信息 |
6. 实战中踩过的坑与排查记录
6.1 Hadoop集群环境类问题
最常遇到的是NameNode启动失败。排查顺序比较固定:先看日志,确认是hostname解析问题还是SSH免密问题,再查端口占用情况和防火墙状态。
YARN任务OOM的问题在低配机器上非常常见。默认的yarn.nodemanager.resource.memory-mb配置的是8G或更大,但你的机器只有4G,任务一跑必然挂。需要手动把yarn-site.xml中的内存参数调小,同时把MapReduce的mapreduce.map.memory.mb也对应调小。这些参数配错时的报错信息往往很迷惑,什么“Java heap space”“Container killed by the ResourceManager”,排查顺序一定要先看YARN日志里实际的container内存使用量。
HDFS小文件问题也非常典型。数据采集脚本如果每天生成几十个几十KB的小文件,会严重拖慢Hive查询。解决思路是:定期用HDFS的archive命令把小文件合并成更大的SequenceFile或ORC文件,或者在采集脚本里直接按周聚合成一个大文件再上传。这个问题在论文里能写一笔,说明你确实有大数据工程的意识。
6.2 深度学习模型训练类问题
模型训练出现NaN loss,最常见原因是数据的特征里有NaN值没处理干净。股票数据停牌、除权、新股上市都会导致空值,这个问题在Hive清洗阶段就必须解决。如果清洗完毕还有NaN,LSTM计算梯度时就会崩溃。
模型只输出单一结果(比如所有预测方向都是跌),这种“模型退化”现象大概率是样本类别不平衡导致的。处理方案有两个:一是对跌的样本进行下采样,让涨跌样本比例接近1比1;二是修改损失函数,比如使用带class_weight的交叉熵。换损失函数后,模型至少不会盲目偏向多数类。
预测曲线总是滞后实际曲线一个交易日,这是时间序列预测的常见现象,本质是模型把“上一日值”当成了最可靠的预测值。要缓解这个问题,一是不要预测绝对值,改为预测收益率或者涨跌方向;二是引入更长的时间窗口;三是增加波动率、成交量等辅助特征,让模型不依赖单一价格信息。答辩时老师非常容易问这个问题,提前准备一个对比图表,展示改进前后的预测效果差异,就能成为加分项。
6.3 交付资料整理类问题
源码、论文、答辩PPT这三样东西要能对得上。源码里的代码文件要和论文里的图表对应,特别是实验结果图,必须确认是当前模型跑出来的,不能随便拿网络截图,否则老师一旦问起细节就无法招架。
源码目录结构建议这样组织:
stock_project/ ├── collect/ # 数据采集脚本 ├── hadoop/ # HDFS上传脚本、Hive建表与清洗SQL ├── feature/ # 特征工程脚本 ├── model/ # 深度学习模型训练与测试 ├── server/ # Flask预测服务 ├── frontend/ # 前端展示页面 ├── sql/ # 建表与查询SQL汇总 ├── docs/ # 论文、答辩PPT、演示视频 └── README.md # 项目说明与运行指南README一定要写清楚环境依赖、启动步骤、数据入口、模型文件位置。答辩前把整条流程在干净环境里从零跑一遍,确认没有依赖缺失。我见过最惨的情况是答辩现场Hadoop启动失败,只能临时切到本地文件系统读取数据,那场面真的很难看。
最后再分享一个小经验
如果你时间有限,别把精力平均分配到每个模块。Hadoop生态部分只要环境搭建好、数据能正常入库、清洗SQL写对,就不要再折腾调优了;深度学习模型部分是论文实验分析的主力,值得多花时间做对比实验和可视化;而系统的Web展示部分,简单能用即可,不要为了好看去研究复杂的前端交互。答辩老师真正关心的是你对整个系统的理解,说到底,论文里“为什么这么做”比“代码怎么写”重要得多,这也是我做了这么多次毕业设计指导之后总结出来的最实在的经验。