数据采集基础:用Python搞定金融与社交媒体数据

各位同学,今天我们来聊聊数据采集。说实话,这个环节是整个模型的地基。地基没打好,后面再漂亮的算法也是空中楼阁。我自己在项目里踩过不少坑,今天把这些经验都掏出来给你们。

核心要点:金融数据 + 社交媒体数据 → 清洗对齐 → 可用数据集

2.1 金融数据获取:yfinance库实战

yfinance这个库,我用它抓过美股、港股、A股的数据。说白了,它就是雅虎财经的Python封装,简单到令人发指。

安装就一行命令:

pip install yfinance

我习惯这样写获取代码:

import yfinance as yf
import pandas as pd

# 获取某只股票的历史数据
ticker = "AAPL"
start_date = "2024-01-01"
end_date = "2024-12-31"

data = yf.download(ticker, start=start_date, end=end_date)
print(data.head())

你想想看,就这么几行代码,开盘价、收盘价、最高价、最低价、成交量全都有了。嗯,这里要注意——yfinance返回的是DataFrame,索引是日期,列名是英文。

我的小技巧:我一般会加个参数 auto_adjust=True,这样拿到的价格是复权后的,省得自己手动调整分红拆股。

获取多只股票也很简单:

tickers = ["AAPL", "MSFT", "GOOGL"]
data = yf.download(tickers, start="2024-01-01", end="2024-12-31")
# 返回的是MultiIndex DataFrame,列名是 (Price_Type, Ticker)

为什么会这样?因为雅虎财经把不同股票的数据堆在一起了。我个人习惯用 .xs() 方法提取某只股票的数据:

aapl_close = data.xs("AAPL", level=1, axis=1)["Close"]

2.2 社交媒体数据获取:Tweepy与微博API

金融数据只是半边天。市场情绪从哪来?社交媒体啊!

我曾经做过一个项目,发现推特上的负面情绪比财报数据提前两天反映股价波动。所以这块数据,必须拿下。

2.2.1 Tweepy 获取推特数据

先装库:

pip install tweepy

然后你需要去Twitter Developer Portal申请API密钥。这个流程有点烦,但没办法。

import tweepy

# 配置API密钥
bearer_token = "你的Bearer Token"

client = tweepy.Client(bearer_token=bearer_token)

# 搜索最近7天的推文
query = "AAPL stock"
tweets = client.search_recent_tweets(query=query, max_results=100)

for tweet in tweets.data:
    print(tweet.text)

避坑指南:我曾经因为没处理API限流,程序跑一半就挂了。免费版每15分钟只能请求450次。建议加个time.sleep(),或者用tweepy自带的等待机制。

2.2.2 微博API获取数据

微博API的申请门槛比推特高一些。不过如果你有企业认证,流程会顺畅很多。

import requests
import json

# 微博API配置
app_key = "你的App Key"
app_secret = "你的App Secret"
access_token = "你的Access Token"

# 搜索微博内容
url = "https://api.weibo.com/2/statuses/public_timeline.json"
params = {
    "access_token": access_token,
    "count": 50
}

response = requests.get(url, params=params)
data = response.json()

for status in data["statuses"]:
    print(status["text"])

说实话,微博API返回的数据结构比推特复杂。我建议先打印出来看看字段结构,再决定提取哪些信息。

2.3 数据清洗与对齐

数据拿到手了,但问题来了——金融数据是每天一条,社交媒体数据是每分钟几十条。怎么对齐?

我一般分三步走:

  1. 清洗金融数据:处理缺失值、去除停牌日
  2. 清洗社交媒体数据:去重、过滤垃圾内容、情感打分
  3. 时间对齐:按日聚合社交媒体数据,与金融数据匹配

2.3.1 金融数据清洗

# 处理缺失值
data = data.dropna()  # 或者用 data.fillna(method='ffill')

# 只保留交易日
data = data[data['Volume'] > 0]

2.3.2 社交媒体数据清洗

import re
from datetime import datetime

def clean_tweet(text):
    # 去除URL
    text = re.sub(r'http\S+', '', text)
    # 去除@提及
    text = re.sub(r'@\w+', '', text)
    # 去除特殊字符
    text = re.sub(r'[^\w\s]', '', text)
    return text.strip()

# 假设tweets_df是包含推文数据的DataFrame
tweets_df['clean_text'] = tweets_df['text'].apply(clean_tweet)
# 过滤掉空文本
tweets_df = tweets_df[tweets_df['clean_text'] != '']

2.3.3 时间对齐

这是最关键的步骤。我习惯把社交媒体数据按天聚合,计算每日情感得分:

# 假设tweets_df有created_at列
tweets_df['date'] = pd.to_datetime(tweets_df['created_at']).dt.date

# 按天计算情感得分(这里用简单的正面/负面词计数)
def sentiment_score(text):
    positive_words = ['up', 'gain', 'profit', 'bullish', 'buy']
    negative_words = ['down', 'loss', 'bearish', 'sell', 'crash']
    score = 0
    for word in positive_words:
        if word in text.lower():
            score += 1
    for word in negative_words:
        if word in text.lower():
            score -= 1
    return score

tweets_df['sentiment'] = tweets_df['clean_text'].apply(sentiment_score)

# 按天聚合
daily_sentiment = tweets_df.groupby('date')['sentiment'].mean().reset_index()
daily_sentiment.columns = ['date', 'avg_sentiment']

# 与金融数据合并
financial_data = yf.download("AAPL", start="2024-01-01", end="2024-12-31")
financial_data['date'] = financial_data.index.date

merged_data = pd.merge(financial_data, daily_sentiment, on='date', how='left')
# 没有社交媒体数据的日期,用前一天的填充
merged_data['avg_sentiment'] = merged_data['avg_sentiment'].fillna(method='ffill')

我的经验:对齐的时候,一定要检查日期范围是否匹配。我曾经因为时区问题,导致金融数据和社交媒体数据错位了一天。建议统一用UTC时间。

2.4 本章知识体系

下面这张图,是我自己梳理的数据采集流程。你看一眼,心里就有谱了。

数据采集与清洗对齐流程 金融数据源 yfinance / 雅虎财经 社交媒体数据源 Tweepy / 微博API 数据清洗 去重 / 过滤 / 处理缺失 时间对齐 按日聚合 / 时区统一 / 日期匹配 融合数据集 金融指标 + 情感得分 + 日期索引 模型输入数据 数据采集 清洗对齐 输出

这张图把整个流程串起来了。从左到右,从上到下,每一步都有对应的代码实现。你跟着走一遍,基本不会出大问题。

最后提醒一句:API密钥千万别提交到GitHub。我见过太多人因为这个被扣费。建议用环境变量或者配置文件管理密钥。

好了,数据采集这块就讲到这里。代码都给了,流程也画了,剩下的就是你自己动手跑一遍。记住,数据质量决定模型上限,别在这个环节偷懒。


专注资料整理