机器学习8 KMeans和DBSCAN分别对销售数据表聚类 对比

导入库

import pandas as pd 
import numpy as np
from sklearn.cluster import KMeans
from sklearn.cluster import DBSCAN
from matplotlib import pyplot as plt

KMeans

这个前面都写过,下面是一个完整的流程,可以自己实践完整写一遍
在这里插入图片描述

DBSCAN

直接看全文代码吧,DBSCAN在后半部分

全文代码

在这里插入图片描述

import pandas as pd 
import numpy as np
from sklearn.cluster import KMeans
from sklearn.cluster import DBSCAN
from matplotlib import pyplot as plt

### KMeans算法

#### 准备数据集

data = pd.read_csv('销售利润表.csv')
data

data.shape

data.info()

data.head()

data.describe()

data.drop(columns="Unnamed: 0",inplace=True) #删除未命名那列

data.head()

#### 构建KMeans模型

KMeans?

km = KMeans(n_clusters=8,max_iter=300,tol=0.01) #写km = KMeans()也可以,因为是默认值

#### 训练模型

km.fit(data)

#### 查看属性

#质心
km.cluster_centers_

#属于哪个簇
km.labels_

#误差平方和
km.inertia_

#### 最优模型(调参)

result = []
for n_clusters in range(2,10):
    for max_iter in range(300,601,50): #最大迭代次数
        for tol in range(2,10):
            tol=tol*1e-5
            km = KMeans(n_clusters=n_clusters,max_iter=max_iter,tol=tol)
            km.fit(data)
            d={'n_clusters':n_clusters,'max_iter':max_iter,'tol':tol,'inertia':km.inertia_}
            result.append(d)
# 一个模型的参数放在字典d里面,用result.append(d)把所有模型的参数存起来到result列表

result

result_df = pd.DataFrame(result) #主要DataFrame的DF都大写
result_df

#导出DataFrame
#outputpath='C:/Users/DANNY/Desktop/DataFrame导出.csv'
#result_df.to_csv(outputpath,sep=',',index=False,header=True)

# 找到误差平方和最小时,对应的那一行的各项参数

result_df["inertia"].argmin() #想找到inertia列的最小值

r=result_df.iloc[result_df["inertia"].argmin(),:] #用iloc[]定位那一行,列都要

#注意,KMeans找拐点才是更准确的,这里只是找了最小簇内平方和

r

#type(r) #如果查看r类型发现上图是pandas中的一维图Series

n_clusters = r["n_clusters"]
n_clusters #簇

max_iter = r["max_iter"]
max_iter #最大迭代数

tol = r['tol']
tol #总的误差平方和

tol = int(tol) #下一行绘图时发现tol不是int报错,所以提前强转

#### 绘图

x=[]
y=[]
for n_clusters in range(2,20):
    km=KMeans(n_clusters=n_clusters,max_iter=max_iter,tol=tol)
    km.fit(data)
    #保存
    x.append(n_clusters)
    y.append(km.inertia_)

x

y

#绘图 
plt.figure(figsize=(20,8))
plt.plot(x,y,"o-")
plt.xlabel('K')
plt.ylabel('inertia')
plt.title('k-inertia relation')
#将数字标注到折线图
for a,b in zip(x,y):
    plt.text(a,b,round(b,0),ha='center',va='bottom')

#结论
聚类的簇 7-10个皆可

#### 相对较优参数进行 可视化呈现(簇状图)

clf = KMeans(n_clusters=5,max_iter=600,tol=8e-5)
clf.fit(data)

clf.cluster_centers_ #质心

clf.labels_ #所属簇标签

clf.inertia_ #误差平方和

#绘图
plt.figure(figsize=(20,8))

plt.scatter(data['销售价格'],data['利润'],c=clf.labels_,marker='x') #scatter画散点图
plt.scatter(clf.cluster_centers_[:,0],clf.cluster_centers_[:,1],c='red')

plt.xlabel('price')
plt.ylabel('profit')
plt.title('KMeans-Sales profit Data')

plt.show() #注意写()


### DBSCAN

#### 构建模型

db=DBSCAN()

#### 训练模型

db.fit(data)

#### 查看属性

#核心点索引
db.core_sample_indices_

#核心点
db.components_

#每个样本所属的簇
labels = db.labels_
labels

type(labels) #numpy的数组

#查看是否有噪声点
if -1 in labels:
    print('有噪声点')
else:
    print('没有噪声点')

#查看噪声点个数
noise = list(labels).count(-1)
print("噪声点的个数:{}".format(noise))

#簇的个数
num_clusters = len(set(labels))-(1 if -1 in labels else 0)
print("簇的个数:{}".format(num_clusters))

#### 调参寻找最优模型

result = []
for r in range(2,20):
    eps=r*1e-2 #把eps单独做个变量优化算法
    for min_samples in range(2,20):
        db=DBSCAN(eps=eps,min_samples=min_samples)
        db.fit(data)
        labels=db.labels_
        
        noise=list(labels).count(-1)#噪声点个数
        num_clusters=len(set(labels))-(1 if -1 in labels else 0)#簇的个数
        
        d={"eps":eps,"min_samples":min_samples,"noise":noise,"num_cluster":num_clusters}
        result.append(d)

result

df=pd.DataFrame(result)

df

df["num_cluster"].min() #发现最少都有17个簇,尽量少一点

#for min_samples in range(2,20):  这一行range(2,10)改成(2,20)就只剩七个了
#反正就是不断的调 半径eps和密度min_samples的range范围

df[df["num_cluster"]==7] #输出簇为7的相关行的参数

df[df.noise == df.noise.min()] #看看噪声最少时的参数

#### 可视化呈现

plt.figure(figsize=(20,8))

plt.scatter(data["销售价格"],data["利润"],c=labels)
plt.scatter(db.components_[:,0],db.components_[:,-1],c='red')

plt.xlabel("price")
plt.ylabel("profit")
plt.title("DBSCAN-Sales profit Data")

plt.show()

### 结论

数据集的密度不稠密,聚类质量较差,DBSCAN不太适合,建议用KMeans
  • 1
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值