关于numpy中cov(x)与cover(x,y)的一些理解

本文详细解析了NumPy库中np.cov与np.var函数的使用方法及区别,特别是np.cov在处理单一数组与多维数组时的不同表现,并通过实例对比np.cov与np.var计算方差的方法。

1. np.cov(x)

x=[1,2,3,4]
np.cov(x)

输出为 array(1.6666666666666665),一开始我以为当x为一个行向量时,cov(x)计算的就是x的方差。但是通过观察发现

np.var(x)*4     #output:5
np.cov(x)*3     #output:5

np.cov(x)这种情况计算的是x方差的无偏估计,即s2=ni=1(xx^)n1,而np.var(x)计算的则是s2=ni=1(xx^)n

接着我们再假设x为一个4*3的矩阵

X=np.array([[1 ,5 ,6] ,[4 ,3 ,9 ],[ 4 ,2 ,9],[ 4 ,7 ,2]])
np.cov(x)

首先不同于matlab。在numpy中,将x的每一列视作一个独立的变量,因此这里一共有3个4维的变量,因此将会输出一个4*4的协方差矩阵
这里写图片描述
其中对角线元素是每个维度的方差,非对角线上的元素则是不同维度间的协方差。

2. np.cov(x,y)

在学习的过程中还有一点比较困惑的是np.cov(x)和np.cov(x,y)的区别,以下用代码来进行说明:

X=np.array([[1 ,5 ,6] ,[4 ,3 ,9 ],[ 4 ,2 ,9],[ 4 ,7 ,2]])
x=X[0:2]
y=X[2:4]
print(np.cov(X))
print(np.cov(x,y))

输出为
这里写图片描述
可以看出两者的输出是相同的。因此所谓的np.cov(X)其实就是把np.cov(x,y)中两个变量所有的维度纵向拼接在一起作为X参与运算。

import numpy as np import pandas as pd import matplotlib.pyplot as plt # 固定随机种子 np.random.seed(0) # 1. 构建候选站点需求节点 num_cand = 600 # 候选站点数 num_dem = 200 # 需求节点数 coords = np.random.rand(num_cand, 2) * 10 dem_coords = np.random.rand(num_dem, 2) * 10 dem_weight = np.random.rand(num_dem) * 10 + 5 # 需求权重 # 2. 站点参数:功率、成本、所属电网片区 power = np.full(num_cand, 120) # kW cost = (150 + 50 * np.random.rand(num_cand)) # 万元 # 划分3x3电网片区 region_x = np.floor(coords[:, 0] / (10/3)).astype(int) region_y = np.floor(coords[:, 1] / (10/3)).astype(int) regions = region_x * 3 + region_y R = 9 C_r = np.random.rand(R) * 1000 + 500 # 片区峰值容量 (kW) # 3. 覆盖半径 v = 0.5 # km/min thr = 10 # min radius = v * thr # 计算覆盖矩阵 dists = np.sqrt(((coords[:, None, :] - dem_coords[None, :, :])**2).sum(axis=2)) cover = dists <= radius # 4. 贪心算法选址 selected = [] covered = np.zeros(num_dem, bool) metrics = [] for k in range(500): best, best_score = None, -1 for j in range(num_cand): if j in selected: continue # 新增覆盖需求 new_cov_weight = dem_weight[~covered & cover[j]].sum() score = new_cov_weight / cost[j] if score > best_score: best, best_score = j, score selected.append(best) covered |= cover[best] # 计算指标 cov_ratio = (dem_weight[covered].sum()) / dem_weight.sum() # 计算电网片区瞬时负荷比 util = np.minimum(1, (cover[selected] * dem_weight).sum(axis=1) / dem_weight.sum()) L_r = np.zeros(R) for idx, j in enumerate(selected): L_r[regions[j]] += power[j] * util[idx] max_lr = (L_r / C_r).max() total_cost = cost[selected].sum() metrics.append([len(selected), cov_ratio, max_lr, total_cost]) df = pd.DataFrame(metrics, columns=['n','Coverage','MaxLoadRatio','Cost']) final = df.iloc[-1:] final # 设置matplotlib支持中文显示 plt.rcParams["font.family"] = ["SimHei", "WenQuanYi Micro Hei", "Heiti TC", "Arial"] plt.rcParams['axes.unicode_minus'] = False # 解决负号显示问题 plt.rcParams.update({'font.size': 12}) # 其余代码保持不变... plt.figure() plt.scatter(dem_coords[:,0], dem_coords[:,1], s=8, label='需求节点') sel_coords = coords[selected] plt.scatter(sel_coords[:,0], sel_coords[:,1], marker='s', s=20, label='选中站点') for x,y in sel_coords[:30]: circle = plt.Circle((x,y), radius, fill=False, linewidth=0.5) plt.gca().add_patch(circle) plt.title('站点布局需求覆盖范围') plt.xlabel('X坐标'); plt.ylabel('Y坐标') plt.legend(); plt.grid(True) # 7. 可视化2:每片区负荷比柱状图 plt.figure() load_ratios = (L_r / C_r) plt.bar(np.arange(R), load_ratios) plt.axhline(0.3, linestyle='--', label='0.3阈值') plt.title('区域最大负荷比') plt.xlabel('区域索引'); plt.ylabel('负荷比') plt.legend(); plt.grid(True) # 8. 可视化3:覆盖率 vs 建设成本 plt.figure() plt.plot(df['Cost'], df['Coverage'], marker='o') plt.title('覆盖率 vs 总成本') plt.xlabel('总成本 (万元)'); plt.ylabel('覆盖率') plt.grid(True) # 9. 可视化4:成本 vs 峰值负荷比 Pareto plt.figure() plt.scatter(df['Cost'], df['MaxLoadRatio']) plt.axhline(0.3, linestyle='--', label='负荷约束') plt.title('成本 vs 最大负荷比 (帕累托)') plt.xlabel('总成本 (万元)'); plt.ylabel('最大负荷比') plt.legend(); plt.grid(True) plt.show()
05-30
评论 3
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值