Python数据分析快速入门手册

Scroll Down

Python数据分析快速入门手册

目录

  1. Python环境配置
  2. Python基础速成
  3. 数据分析核心库
  4. 数据可视化库
  5. 实战案例
  6. 常用技巧与资源

环境配置

推荐安装方式

# 安装Miniconda(轻量级Anaconda)
# 下载地址:https://docs.conda.io/en/latest/miniconda.html

# 或使用pip直接安装
pip install numpy pandas matplotlib seaborn jupyter scikit-learn

Jupyter Notebook使用

# 启动Jupyter
jupyter notebook

# 或在VSCode中直接使用
# 安装Python扩展和Jupyter扩展

Python基础

1. 基本数据类型

# 变量与基本类型
x = 10           # 整数
y = 3.14         # 浮点数
name = "数据分析" # 字符串
is_valid = True  # 布尔值

# 列表(可变)
data_list = [1, 2, 3, 4, 5]
data_list.append(6)

# 元组(不可变)
data_tuple = (1, 2, 3)

# 字典
data_dict = {"name": "John", "age": 25, "city": "Beijing"}

# 集合
data_set = {1, 2, 3, 4, 5}

2. 控制流

# 条件判断
score = 85
if score >= 90:
    grade = "A"
elif score >= 80:
    grade = "B"
else:
    grade = "C"

# 循环
# for循环
for i in range(5):
    print(i)

# while循环
count = 0
while count < 5:
    print(count)
    count += 1

3. 函数定义

def calculate_mean(numbers):
    """计算平均值"""
    return sum(numbers) / len(numbers)

# 使用lambda函数
square = lambda x: x ** 2

4. 列表推导式

# 简洁的列表创建方式
squares = [x**2 for x in range(10)]
even_numbers = [x for x in range(20) if x % 2 == 0]

数据分析核心库

1. NumPy - 数值计算基础

import numpy as np

# 创建数组
arr = np.array([1, 2, 3, 4, 5])
matrix = np.array([[1, 2, 3], [4, 5, 6]])

# 常用操作
zeros = np.zeros((3, 4))      # 3x4的零矩阵
ones = np.ones((2, 3))        # 2x3的全1矩阵
random_arr = np.random.rand(5)  # 随机数组

# 数组运算
arr1 = np.array([1, 2, 3])
arr2 = np.array([4, 5, 6])
sum_arr = arr1 + arr2          # 对应元素相加
dot_product = np.dot(arr1, arr2)  # 点积

# 统计函数
mean_value = np.mean(arr)
std_value = np.std(arr)
max_value = np.max(arr)
min_value = np.min(arr)

2. Pandas - 数据处理核心

import pandas as pd

# 创建DataFrame
data = {
    '姓名': ['张三', '李四', '王五', '赵六'],
    '年龄': [25, 30, 35, 28],
    '城市': ['北京', '上海', '广州', '深圳'],
    '薪资': [5000, 8000, 6000, 7000]
}
df = pd.DataFrame(data)

# 基本操作
print(df.head())       # 查看前5行
print(df.info())       # 数据信息
print(df.describe())   # 统计描述

# 数据选择
df['年龄']            # 选择单列
df[['姓名', '薪资']]   # 选择多列
df.iloc[0:3]          # 按位置选择行
df.loc[df['年龄'] > 28]  # 按条件选择

# 数据清洗
df.dropna()           # 删除缺失值
df.fillna(0)          # 填充缺失值
df.drop_duplicates()  # 删除重复值

# 数据转换
df['薪资等级'] = df['薪资'].apply(lambda x: '高' if x > 7000 else '中' if x > 5500 else '低')

# 分组聚合
grouped = df.groupby('城市')['薪资'].agg(['mean', 'count', 'sum'])

数据可视化库

1. Matplotlib - 基础绘图

import matplotlib.pyplot as plt
import numpy as np

# 设置中文字体(解决中文乱码)
plt.rcParams['font.sans-serif'] = ['SimHei', 'Microsoft YaHei']
plt.rcParams['axes.unicode_minus'] = False

# 折线图
x = np.linspace(0, 10, 100)
y = np.sin(x)

plt.figure(figsize=(10, 6))
plt.plot(x, y, label='sin(x)', color='blue', linewidth=2)
plt.title('正弦函数曲线')
plt.xlabel('X轴')
plt.ylabel('Y轴')
plt.legend()
plt.grid(True, alpha=0.3)
plt.show()

# 散点图
plt.figure(figsize=(8, 6))
plt.scatter(df['年龄'], df['薪资'], c='red', alpha=0.6)
plt.title('年龄与薪资关系')
plt.xlabel('年龄')
plt.ylabel('薪资')
plt.show()

# 柱状图
categories = ['A', 'B', 'C', 'D']
values = [23, 45, 56, 78]

plt.figure(figsize=(8, 6))
plt.bar(categories, values, color=['red', 'green', 'blue', 'orange'])
plt.title('分类数据柱状图')
plt.xlabel('类别')
plt.ylabel('数值')
plt.show()

# 直方图
data = np.random.randn(1000)
plt.figure(figsize=(8, 6))
plt.hist(data, bins=30, alpha=0.7, color='skyblue', edgecolor='black')
plt.title('数据分布直方图')
plt.xlabel('数值')
plt.ylabel('频率')
plt.show()

# 子图
fig, axes = plt.subplots(2, 2, figsize=(12, 10))

axes[0, 0].plot(x, y)
axes[0, 0].set_title('子图1')

axes[0, 1].scatter(x, np.cos(x))
axes[0, 1].set_title('子图2')

axes[1, 0].bar(categories, values)
axes[1, 0].set_title('子图3')

axes[1, 1].hist(data, bins=20)
axes[1, 1].set_title('子图4')

plt.tight_layout()
plt.show()

2. Seaborn - 高级统计图表

import seaborn as sns

# 设置样式
sns.set_style("whitegrid")
sns.set_palette("husl")

# 加载示例数据
tips = sns.load_dataset("tips")

# 箱线图
plt.figure(figsize=(10, 6))
sns.boxplot(x='day', y='total_bill', data=tips)
plt.title('不同日期消费箱线图')
plt.show()

# 小提琴图
plt.figure(figsize=(10, 6))
sns.violinplot(x='day', y='total_bill', hue='sex', data=tips, split=True)
plt.title('消费分布小提琴图')
plt.show()

# 热力图
correlation = tips.corr()
plt.figure(figsize=(8, 6))
sns.heatmap(correlation, annot=True, cmap='coolwarm', center=0)
plt.title('相关性热力图')
plt.show()

# 分布图
plt.figure(figsize=(10, 8))
sns.jointplot(x='total_bill', y='tip', data=tips, kind='scatter')
plt.suptitle('消费与小费关系分布图')
plt.show()

# 配对图
sns.pairplot(tips, hue='sex', diag_kind='kde')
plt.suptitle('多变量配对图', y=1.02)
plt.show()

3. Plotly - 交互式图表

# 安装:pip install plotly
import plotly.express as px
import plotly.graph_objects as go

# 使用示例数据
df = px.data.gapminder().query("year == 2007")

# 散点图(交互式)
fig = px.scatter(df, x="gdpPercap", y="lifeExp", 
                 size="pop", color="continent",
                 hover_name="country", 
                 log_x=True, size_max=60,
                 title="2007年各国GDP与预期寿命")
fig.show()

# 3D散点图
fig = px.scatter_3d(df, x='gdpPercap', y='lifeExp', z='pop',
                    color='continent', hover_name='country')
fig.show()

实战案例

案例1:销售数据分析

import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
import numpy as np

# 创建模拟销售数据
np.random.seed(42)
dates = pd.date_range('2023-01-01', '2023-12-31', freq='D')
sales_data = pd.DataFrame({
    '日期': dates,
    '销售额': np.random.normal(10000, 2000, len(dates)),
    '订单数': np.random.poisson(50, len(dates)),
    '产品类别': np.random.choice(['电子产品', '服装', '食品', '家居'], len(dates)),
    '客户类型': np.random.choice(['新客户', '老客户'], len(dates), p=[0.3, 0.7])
})

# 添加季节趋势
sales_data['销售额'] = sales_data['销售额'] * (1 + 0.3 * np.sin(2 * np.pi * sales_data['日期'].dt.dayofyear / 365))

print("数据概览:")
print(sales_data.head())
print("\n基本统计:")
print(sales_data.describe())

# 月度销售分析
sales_data['月份'] = sales_data['日期'].dt.month
monthly_sales = sales_data.groupby('月份')['销售额'].agg(['sum', 'mean', 'std'])

# 可视化
fig, axes = plt.subplots(2, 2, figsize=(15, 12))

# 1. 月度销售额趋势
axes[0, 0].plot(monthly_sales.index, monthly_sales['sum'], marker='o', linewidth=2)
axes[0, 0].set_title('月度销售额趋势')
axes[0, 0].set_xlabel('月份')
axes[0, 0].set_ylabel('销售额')
axes[0, 0].grid(True, alpha=0.3)

# 2. 产品类别销售额
category_sales = sales_data.groupby('产品类别')['销售额'].sum()
axes[0, 1].bar(category_sales.index, category_sales.values)
axes[0, 1].set_title('各产品类别销售额')
axes[0, 1].set_xlabel('产品类别')
axes[0, 1].set_ylabel('销售额')
axes[0, 1].tick_params(axis='x', rotation=45)

# 3. 销售额分布
axes[1, 0].hist(sales_data['销售额'], bins=30, alpha=0.7, color='skyblue', edgecolor='black')
axes[1, 0].set_title('销售额分布')
axes[1, 0].set_xlabel('销售额')
axes[1, 0].set_ylabel('频数')

# 4. 客户类型对比
customer_sales = sales_data.groupby('客户类型')['销售额'].agg(['mean', 'count'])
axes[1, 1].bar(customer_sales.index, customer_sales['mean'])
axes[1, 1].set_title('不同类型客户平均销售额')
axes[1, 1].set_xlabel('客户类型')
axes[1, 1].set_ylabel('平均销售额')

plt.tight_layout()
plt.show()

# 相关性分析
correlation_matrix = sales_data[['销售额', '订单数']].corr()
print("\n相关性矩阵:")
print(correlation_matrix)

案例2:用户行为分析

# 用户行为分析
# 创建模拟用户数据
np.random.seed(123)
user_data = pd.DataFrame({
    '用户ID': range(1, 101),
    '年龄': np.random.randint(18, 60, 100),
    '性别': np.random.choice(['男', '女'], 100),
    '注册天数': np.random.randint(1, 1000, 100),
    '活跃天数': np.random.randint(1, 500, 100),
    '消费金额': np.random.exponential(1000, 100),
    '点击次数': np.random.poisson(50, 100)
})

# 计算用户价值
user_data['日均活跃'] = user_data['活跃天数'] / user_data['注册天数']
user_data['用户价值'] = (user_data['消费金额'] / user_data['注册天数']) * 100

# RFM分析
def calculate_rfm_score(data):
    """计算RFM得分"""
    # Recency:最近活跃(这里用注册天数代替)
    # Frequency:活跃频率(日均活跃)
    # Monetary:消费金额
    data['R_score'] = pd.qcut(data['注册天数'], 4, labels=[4, 3, 2, 1])
    data['F_score'] = pd.qcut(data['日均活跃'], 4, labels=[1, 2, 3, 4])
    data['M_score'] = pd.qcut(data['消费金额'], 4, labels=[1, 2, 3, 4])
    return data

user_data = calculate_rfm_score(user_data)
user_data['RFM总分'] = user_data['R_score'].astype(int) + user_data['F_score'].astype(int) + user_data['M_score'].astype(int)

# 用户分群
def segment_users(rfm_score):
    if rfm_score >= 10:
        return '高价值用户'
    elif rfm_score >= 7:
        return '中价值用户'
    else:
        return '低价值用户'

user_data['用户分群'] = user_data['RFM总分'].apply(segment_users)

# 可视化分析
fig, axes = plt.subplots(2, 3, figsize=(18, 12))

# 1. 用户年龄分布
axes[0, 0].hist(user_data['年龄'], bins=15, alpha=0.7, color='lightcoral', edgecolor='black')
axes[0, 0].set_title('用户年龄分布')
axes[0, 0].set_xlabel('年龄')
axes[0, 0].set_ylabel('用户数')

# 2. 性别分布
gender_counts = user_data['性别'].value_counts()
axes[0, 1].pie(gender_counts.values, labels=gender_counts.index, autopct='%1.1f%%', colors=['lightblue', 'lightpink'])
axes[0, 1].set_title('用户性别分布')

# 3. 用户价值分布
segment_counts = user_data['用户分群'].value_counts()
axes[0, 2].bar(segment_counts.index, segment_counts.values, color=['gold', 'orange', 'red'])
axes[0, 2].set_title('用户价值分群')
axes[0, 2].set_xlabel('用户分群')
axes[0, 2].set_ylabel('用户数')

# 4. 年龄与消费关系
axes[1, 0].scatter(user_data['年龄'], user_data['消费金额'], alpha=0.6)
axes[1, 0].set_title('年龄与消费关系')
axes[1, 0].set_xlabel('年龄')
axes[1, 0].set_ylabel('消费金额')

# 5. RFM分布
rfm_scores = user_data['RFM总分'].value_counts().sort_index()
axes[1, 1].plot(rfm_scores.index, rfm_scores.values, marker='o')
axes[1, 1].set_title('RFM总分分布')
axes[1, 1].set_xlabel('RFM总分')
axes[1, 1].set_ylabel('用户数')
axes[1, 1].grid(True, alpha=0.3)

# 6. 热力图:各分群特征
pivot_table = user_data.pivot_table(index='用户分群', values=['年龄', '注册天数', '消费金额'], aggfunc='mean')
sns.heatmap(pivot_table, annot=True, fmt='.1f', cmap='YlOrRd', ax=axes[1, 2])
axes[1, 2].set_title('各用户分群特征对比')

plt.tight_layout()
plt.show()

print("\n用户分群统计:")
print(user_data['用户分群'].value_counts())
print("\n各分群平均消费:")
print(user_data.groupby('用户分群')['消费金额'].mean())

常用技巧

1. 数据清洗技巧

# 处理缺失值
def handle_missing_values(df):
    # 检查缺失值
    missing = df.isnull().sum()
    print("缺失值统计:")
    print(missing[missing > 0])
    
    # 填充策略
    # 数值型:用均值填充
    numeric_cols = df.select_dtypes(include=[np.number]).columns
    df[numeric_cols] = df[numeric_cols].fillna(df[numeric_cols].mean())
    
    # 分类型:用众数填充
    categorical_cols = df.select_dtypes(include=['object']).columns
    for col in categorical_cols:
        df[col] = df[col].fillna(df[col].mode()[0])
    
    return df

# 异常值处理
def remove_outliers(df, column):
    Q1 = df[column].quantile(0.25)
    Q3 = df[column].quantile(0.75)
    IQR = Q3 - Q1
    lower_bound = Q1 - 1.5 * IQR
    upper_bound = Q3 + 1.5 * IQR
    return df[(df[column] >= lower_bound) & (df[column] <= upper_bound)]

2. 数据分析模板

class DataAnalyzer:
    def __init__(self, data_path):
        self.data = pd.read_csv(data_path)
        
    def quick_analysis(self):
        """快速分析报告"""
        print("="*50)
        print("数据快速分析报告")
        print("="*50)
        print(f"数据形状: {self.data.shape}")
        print(f"\n数据类型:")
        print(self.data.dtypes)
        print(f"\n缺失值统计:")
        print(self.data.isnull().sum())
        print(f"\n描述性统计:")
        print(self.data.describe())
        print(f"\n前5行数据:")
        print(self.data.head())
        
    def visualize_distributions(self, columns=None):
        """可视化数值分布"""
        if columns is None:
            columns = self.data.select_dtypes(include=[np.number]).columns
        
        fig, axes = plt.subplots(len(columns), 2, figsize=(12, 4*len(columns)))
        
        for i, col in enumerate(columns):
            # 直方图
            axes[i, 0].hist(self.data[col].dropna(), bins=30, alpha=0.7, color='skyblue', edgecolor='black')
            axes[i, 0].set_title(f'{col}分布直方图')
            axes[i, 0].set_xlabel(col)
            axes[i, 0].set_ylabel('频数')
            
            # 箱线图
            axes[i, 1].boxplot(self.data[col].dropna())
            axes[i, 1].set_title(f'{col}箱线图')
            axes[i, 1].set_ylabel(col)
        
        plt.tight_layout()
        plt.show()
    
    def correlation_analysis(self):
        """相关性分析"""
        numeric_data = self.data.select_dtypes(include=[np.number])
        correlation = numeric_data.corr()
        
        plt.figure(figsize=(10, 8))
        sns.heatmap(correlation, annot=True, cmap='coolwarm', center=0, fmt='.2f')
        plt.title('变量相关性热力图')
        plt.show()
        
        return correlation

3. 性能优化技巧

# 使用向量化操作替代循环
# 慢的方法
result = []
for value in data:
    result.append(value * 2)

# 快的方法(向量化)
result = data * 2

# 使用pandas内置函数
# 慢的方法
df['new_col'] = df['col'].apply(lambda x: process(x))

# 快的方法(如果可能)
df['new_col'] = process(df['col'])

# 使用合适的数据类型
# 将分类数据转换为category类型
df['category_column'] = df['category_column'].astype('category')

学习资源

在线资源

  1. 官方文档

  2. 学习平台

  3. 数据集资源

    • UCI Machine Learning Repository
    • Kaggle Datasets
    • 国家统计局公开数据

推荐书籍

  1. 《利用Python进行数据分析》(Wes McKinney)
  2. 《Python数据科学手册》(Jake VanderPlas)
  3. 《统计学习方法》(李航)

最佳实践

  1. 始终从理解业务问题开始
  2. 数据清洗占80%的工作时间
  3. 可视化是理解数据的关键
  4. 记录每一步分析过程
  5. 保持代码可重复性