复合式统计图绘制方法(1)
常用的统计图有条形图、柱形图、折线图、曲线图、饼图、环形图、扇形图。
前几类图比较容易绘制,饼图环形图绘制较难。
在统计图的应用方面,有时候有两个关联的统计学的样本值要用统计图来表达,一张统计图不能表达清楚,就要二张图来表达。由此就产生了复合式的统计图,它能将两个需要表达的统计概念统一在一张图表上阐述清楚。
今在此提供一种复合式统计图的绘制方法供参考。
对于样本值的处理,代码中提供了一种计算方法。
下面是绘制复合式统计图( 雷达图 外套环形图 )的代码:
//变量: 可设置成全局变量或私有变量
Canvas cs ; //画布,绘制图表载体
float pi=3.1415926535 ;
float a ; //三角函数 sin (a), cos (a),
float r ; //圆半径 radius
int i, j, n ;
float x0,y0,x1,y1 ; //作图
float dx,dy ; //中心坐标
string ss, ss1, ss2 ; //打印文字
int p[6] ; //set data or input data
double pn ; //显示数据
int cr, cg, cb ; //设置颜色 setColor (a,r,g,b)
//*************************
compound1 (){ //统计复合图:雷达图加环图
cs.ClearDraw (0,src); //清屏
clearOutput();
selectStyle () ; //图例样式选项设置
cs.SetFillMode (1);//0不填色,1填色
cs.SetColor (255,250,250,250);
cs.DrawRect (0,4,720,600); //back board
cs.SetColor (255,140,140,140);
cs.DrawRect (24,24,706,586); //back
cs.SetColor (255,180,180,250);
cs.SetColor (255,230,240,250);
cs.DrawRect (20,20,700,580); //back
cs.SetColor (255,200,220,250);
cs.DrawRect (40,35,135,185); //色标底左
cs.SetColor (255,180,190,250);
cs.DrawRect (40,185,135,340); //色标底
cs.SetColor (255,140,160,250);
cs.DrawRect (40,340,135,490); //色标底
cs.SetColor (255,200,220,250);
cs.DrawRect (585,200,680,440); //色标底右
cs.SetFillMode (0);//0不填色,1填色
cs.SetColor (255,0,0,240);
cs.DrawRect (20,20,700,580); //框线
cs.DrawRect (24,24,696,576); //框线
//*************************
double sum1, sum2, sum3, sum ;
double sum4, sum5, sum6 ;
//绘制环形图加雷达图,先绘制环形图
cs.SetFillMode (1);//0不填色,1填色
cs.SetStrokeWidth(2); //线
dx=360; dy=280 ; r=200; //center, radius
p[1]=143; p[2]=170; p[3]=162 ;
p[4]=180; p[5]=175; p[6]=170 ;
//* 此数值是以样本值换算后的作图数据,
//* 计算方法列后
k[0]=0; //k= -180,12点钟方向为0位
//k=0, 3点钟方向为0位
k[1]=k[0]+p[1]*72/100 ;
k[2]=k[1]+p[2]*72/100 ;
k[3]=k[2]+p[3]*72/100 ;
k[4]=k[3]+p[4]*72/100 ;
k[5]=k[4]+p[5]*72/100 ;
k[6]=k[5]+p[6]*72/100 ;
cs.SetColor(255,250,250,250);
cs.DrawCircle(dx,dy,205); //中心加圆是环图
cs.SetTextStyle (0); //show data
cs.SetTextSize (18);
//绘制环形图
for (n=1; n<=6 ; n++){ //data=5, draw Piegraph
for (i= k[n-1]; i<=k[n]+2; i++){ // +2 尾线圆闭合
a=pi/360*i ; // a/2 绘出的是半圆
if (n==1) cs.SetColor(255,250,0,0);
if (n==2) cs.SetColor(255,250,150,0);
if (n==3) cs.SetColor(255,0,0,250);
if (n==4) cs.SetColor(255,0,250,250);
if (n==5) cs.SetColor(255,250,0,250);
if (n==6) cs.SetColor(255,0,250,0);
x0=(float)(r*cos (a))+dx; //r=radius
y0=(float)(-r*sin (a))+dy; //逆时针
cs.DrawLine (dx,dy,x0,y0); //逐线绘出加色标
cs.DrawRect (590,n*30+225,675,n*30+250);
cs.SetColor(255,250,250,250);
cs.DrawCircle(dx,dy,117); //中心加圆是环图
pn=p[n]*1000 ; //保留1位小数
pn=pn/10000 ;
ss=doubleToString (pn)+"%" ;
ss1=intToString (n)+". "+ss;
cs.SetColor(255,250,250,250);
cs.DrawText(ss1, 600,n*30+243);
cs.SetColor(255,250,250,250); //环图上标( n% )
ma=pi/360*((k[n-1]+k[n])/2) ;
x1=(float)((r-45)*cos (ma))+dx;
y1=(float)(-(r-35)*sin (ma))+dy ;
cs.DrawText (ss,x1-25,y1); //商品色标
cs.Update (); } } //show 环图
//绘制雷达图底图
cs.SetFillMode (0);//0不填色,1填色
cs.SetStrokeWidth(2); //雷达图底线
dx=360; dy=280 ; //center
int cr, cg, cb ; //set color (a,r,g,b)
for (i=1; i<=51 ; i++){ //底图圆渐变色
cb=i*5 ; L=i*2+10;
cs.SetColor(255,50,i*2+90,cb);
cs.DrawCircle(dx,dy,L); } //底图色
cs.SetFillMode (1);//0不填色,1填色
cs.SetColor(255,50,80,0);
cs.DrawCircle(dx,dy,15); //圆心
cs.SetFillMode (0);//0不填色,1填色
cs.SetStrokeWidth(1); //雷达图底线
cs.SetColor(255,250,0,0);
cs.SetTextStyle (0);
cs.SetTextSize (16);
for (i=1; i<=5 ; i++){ //画标线圆和标值
a=pi/360*i ;
x0=(float)(200*cos (a))+dx ;
y0=(float)(200*sin (a))+dy ;
cs.SetFillMode (0);//0不填色,1填色
cs.SetColor(255,250,250,250);
cs.DrawCircle(dx,dy,i*20);
cs.SetFillMode (1);//0不填色,1填色
x1=(float)(i*20*cos (a))+dx ;
y1=(float)(i*20*sin (a))+dy ;
ss=intToString (i*2);
cs.DrawText(ss,x1-8,285); }
cs.SetFillMode (1);//0不填色,1填色
cs.SetTextSize (18);
cs.SetColor(255,250,0,0);
for (i=0; i<=5 ; i++){ //标线六角射线,标字
a=pi/360*i*120 ;
x0=(float)(210*cos(a))+dx ;
y0=(float)(210*sin(a))+dy ;
cs.DrawLine (x0,y0,dx,dy);
x1=(float)(215*cos(a))+dx-5 ;
y1=(float)(-215*sin(a))+dy+5 ; //逆时针
ss=intToString (i+1) ;
cs.DrawText (ss,x1,y1) ; }
cs.SetTextSize (22);
cs.SetColor(255,250,50,120);
cs.DrawText ("1 - 6 ",600,250) ;
cs.DrawText ("商品类 ",600,225) ;
cs.Update ();
sleep(1000);
//雷达图绘制方法:
//input data : 分三组,每组6个分数(或平均分数)
int p1[6], p2[6], p3[6] ;
int L ; //高度,长度
//演示的数据是杜撰的,不代表真实的平均数
cs.SetStrokeWidth(2); //雷达图线
//Draw Group 1 *************
p1[0]=85; //0位,起点
p1[1]=85; p1[2]=68; p1[3]=94;
p1[4]=60; p1[5]=75; p1[6]=88;
cs.SetColor(255,250,0,0); //group 1
L=p1[1] ;
a=pi/360 ;
x0=(float)(L*cos(a))+dx ;
y0=(float)(-L*sin(a))+dy ;
cs.DrawCircle(x0,y0,4);
x2=x0; y2=y0;
for (i=1; i<=5; i++){ //六角射线点
L=p1[i+1] ;
a=pi/360*i*120 ;
x1=(float)(L*cos(a))+dx ;
y1=(float)(-L*sin(a))+dy ; //逆时针
cs.DrawCircle(x1,y1,4);
cs.DrawLine (x2,y2,x1,y1); //连线
x2=x1; y2=y1 ; }
cs.DrawLine (x2,y2,x0,y0); //连线0点
cs.Update ();
for (i=1; i<=6; i++){ //打印色标
ss=intToString (i)+" . "+intToString (p1[i]) ;
cs.DrawText (ss, 60, i*20+60) ; }
cs.DrawText ("Group 1 ", 50, 60) ;
sleep (1000); //逐步展示
//Draw Group 2 ************
p2[0]=65 ;
p2[1]=65; p2[2]=75; p2[3]=70;
p2[4]=80; p2[5]=95; p2[6]=78;
cs.SetColor(255,0,250,0); //group 2
L=p2[1];
a=pi/360 ;
x0=(float)(L*cos(a))+dx ;
y0=(float)(-L*sin(a))+dy ;
cs.DrawCircle(x0,y0,4);
x2=x0; y2=y0;
for (i=1; i<=5; i++){ //六角射线点
L=p2[i+1] ;
a=pi/360*i*120 ;
x1=(float)(L*cos(a))+dx ;
y1=(float)(-L*sin(a))+dy ; //逆时针
cs.DrawCircle(x1,y1,4);
cs.DrawLine (x2,y2,x1,y1); //连线
x2=x1; y2=y1 ; }
cs.DrawLine (x2,y2,x0,y0); //连线回0点
cs.Update ();
for (i=1; i<=6; i++){ //打印色标
ss=intToString (i)+" . "+intToString (p2[i]) ;
cs.DrawText (ss, 60, i*20+210) ; }
cs.DrawText ("Group 2 ", 50, 210) ;
sleep (1000); //逐步展示
//Draw Group 3 ************
p3[0]=75 ;
p3[1]=75; p3[2]=88; p3[3]=85;
p3[4]=97; p3[5]=70; p3[6]=68;
cs.SetColor(255,250,250,0); //group 3
L=p3[1] ;
a=pi/360 ;
x0=(float)(L*cos(a))+dx ;
y0=(float)(-L*sin(a))+dy ;
cs.DrawCircle(x0,y0,4);
x2=x0; y2=y0;
for (i=1; i<=5; i++){ //六角射线点
L=p3[i+1] ;
a=pi/360*i*120 ;
x1=(float)(L*cos(a))+dx ;
y1=(float)(-L*sin(a))+dy ; //逆时针
cs.DrawCircle(x1,y1,4);
cs.DrawLine (x2,y2,x1,y1); //连线
x2=x1; y2=y1 ; }
cs.DrawLine (x2,y2,x0,y0); //连线回0点
for (i=1; i<=6; i++){ //打印色标
ss=intToString (i)+" . "+intToString (p3[i]) ;
cs.DrawText (ss, 60, i*20+360) ; }
cs.DrawText ("Group 3 ", 50, 360) ;
//数据计算方法
//p1(6)={70,95,68,94,60,75} //样本值
//p2(6)={78,65,69,70,85,90}
//p3(6)={50,75,88,85,97,70}
sum=0 ; sum1=0 ; sum2=0 ; sum3=0 ;
sum4=0 ; sum5=0 ; sum6=0 ;
for (n=1; n<=6 ; n++){ //data=6
sum=sum+p[n] ; }
//单个商品按类相加=单个商品总量
//分组6个商品总量相加=商品销售总量
//占比分析:单个商品量/商品销售总量
//商品*单价=销售额
//6个商品类销售额相加=销售总额
//单个销售额/销售总额=单个商品类占比
//占比分析:单个商品类销售总额/商品销售总额
//模拟数据:3组,每组 6 数值。原始数据绘制雷达图
//数据计算示例:
// 商品 Group 计算 calculate
// 序 大类 1 2 3 sum % 环图数据
//-------------------------------------------------
// 1 A 70 78 50 198 14.3 143
// 2 B 95 65 75 235 17.0 170
// 3 C 68 69 88 225 16.2 162
// 4 D 94 70 85 249 18.0 180
// 5 E 60 85 97 242 17.5 175
// 6 F 75 90 70 235 17.0 170
//------------------------------------------------
// 1384 100% 1000
//作图数据以1000换算成720线
//商品类 量比总数
sum1=70+78+50 ; //198
sum2=95+65+75 ; //235
sum3=68+69+88 ; //225
sum4=94+70+85 ; //249
sum5=60+85+97 ; //242
sum6=75+90+70 ; //235 sum=1384
sum=sum1+sum2+sum3+sum4+sum5+sum6 ;
print "pns(3) sum1 = ", sum1 ;
print "pns(3) sum2 = ", sum2 ;
print "pns(3) sum3 = ", sum3 ;
print "pns(3) sum4 = ", sum4 ;
print "pns(3) sum5 = ", sum5 ;
print "pns(3) sum6 = ", sum6 ;
print " sum (1-6) = ", sum ;
//化成百分数*10 ,此为作图数据
pn=sum1/sum*10000/10 ;
pn=(int)pn ; print "sum1 = ",pn ;
pn=sum2/sum*10000 ;
pn=(int)pn ; print "sum2 = ",pn ;
pn=sum3/sum*10000 ;
pn=(int)pn ; print "sum3 = ",pn ;
pn=sum4/sum*10000 ;
pn=(int)pn ; print "sum4 = ",pn ;
pn=sum5/sum*10000 ;
pn=(int)pn ; print "sum5 = ",pn ;
pn=sum6/sum*10000 ;
pn=(int)pn ; print "sum6 = ",pn ;
//****数据计算*******************************
//题标: 艺术立体字制作
cs.SetFillMode (1);//0不填色,1填色
cs.SetTextStyle (1);
cs.SetStrokeWidth(1);
cs.SetTextSize (26);
cs.SetColor(255,0,0,250);
cs.DrawText ("Radar Chart 📊",500,60) ;
cs.SetTextSize (40);
ss="统计图:雷达加扇形复合图" ;
cs.SetColor(255,50,120,20); //立体字
cs.DrawText (ss,124,544); //阴影
cs.SetColor(255,0,250,0);
cs.DrawText (ss,120,540); //本字
cs.SetFillMode (0);//0不填色,1填色
cs.SetColor(255,250,150,0);
cs.DrawText (ss,120,540); //框线
cs.Update ();
}//compound1 ()
//**** END *****************