经验首页 前端设计 程序设计 Java相关 移动开发 数据库/运维 软件/图像 大数据/云计算 其他经验
当前位置:技术经验 » 程序设计 » C 语言 » 查看文章
基于C语言实现计算生辰八字五行的示例详解
来源:jb51  时间:2023/3/29 10:07:37  对本文有异议

本文介绍生辰八字和八字五行的一种算法。站内有人在查询生辰八字的算法,此题本人也感兴趣。故以此文以续貂尾。

生辰八字计算要点是节气日,年柱以立春起,月柱以是月节气日起,故先要计算月首的节气日。本节气算法的节气时刻精度差些,但确定节气日是可以的。程序启动时先计算干支表和对应的五行表。具体的计算方法参阅程序的注释。算法很简单,一看就明白。要注意的是,八字的时柱先输出的是起时,生日时辰十二个时辰对应下面的起时表计算。程序列示文本打印输出和图片显示输出二种方法供参考。

本文主要介绍生辰八字的算法,没有计算农历日期,农历计算较为复杂,加农历算法,加月历打印输出成了万年历了。

以下是计算方法的源码:

  1. Canvas cs ;
  2. string sBarDes[10]; //按钮
  3. int nBarId[10];
  4. float src[4]; //ClearDraw (cls) clear screen
  5. int ds[3] ;
  6. int i,j,t,k; //t = times
  7. string fname; //filename 加底图
  8. int sx, sy, x0, y0 ;
  9. int alln,alln1;
  10. int ns,leap;
  11. double nleap,nleapd; //农历闰月,0无闰,闰月大小
  12. int n,n0,n1,n2 ;
  13. string s,s0,ss,s5,s6 ;
  14. string s1,s2,s3,s4;
  15. string s11, s12, s13, s14 ;
  16.  
  17. int wd ;
  18. string wds,wdss; //weekday
  19. double dy0,dy1,dm1,dd1;
  20. int dy, dm, dd ;
  21. string dy2, dm2, dd2 ; //日期输入dy2
  22. double hh1,mm1,ss1;
  23. string hh2,mm2,ss2;
  24. int gzy,gzm,gzd,gzh; //干支 yy mm dd hh
  25. string gzys,gzms,gzds,gzhs;
  26. int gzn1;
  27. int yz,mz; //年柱 月柱
  28. string gzs, bzs ; //八字
  29. string whss, g12ss,st28ss; //五行 十二建 二十八宿
  30. string tgs, dzs, whs, whs1, whs2 ; //计算五行
  31. int dzd0,dzd1; //冬至日
  32.  
  33. string jqnames ; //节气中文名称
  34. string t1, t2, t3 ; //计算时间串 hh;mm;ss
  35. double jd; //计算节气
  36. double juD,tht,yrD;
  37. double sD; //shouD
  38. double vs,dalt; //solar
  39.  
  40. int jqdn ; //节气计算
  41. int jqd1,jqd2 ;
  42. string jqs1,jqs2;
  43. string jqss1,jqss2;
  44. string jnum,jname1, jname2 ;
  45. main(){
  46. setDisplay(1);
  47. cs.SetBackground(240,240,240);
  48. cs.Active();
  49. sBarDes[0]="输入日期";
  50. nBarId[0]=100;
  51. sBarDes[1]=" ";
  52. nBarId[1]=101;
  53. sBarDes[2]="文本显示";
  54. nBarId[2]=102;
  55. sBarDes[3]="图片显示";
  56. nBarId[3]=103;
  57. sBarDes[4]="退出程序";
  58. nBarId[4]=104;
  59. sBarDes[5]="...";
  60. nBarId[5]=105;
  61. setToolBarHeight(6);
  62. setButtonTextSize(14);
  63. setToolBarBackgroundColor(255,220,220,220);
  64. setButtonColor(255,240,240,240);
  65. setButtonTextColor(255,0,0,120);
  66. setToolBar(100,myToolBarProc,sBarDes,nBarId,6);
  67. setTitle("生辰八字五行计算 ");
  68. //**********
  69. jqnames="小寒大寒立春雨水惊蛰春分清明谷雨立夏小满芒种夏至小暑大暑立秋处暑白露秋分寒露霜降立冬小雪大雪冬至";
  70. wdss="星期日星期一星期二星期三星期四星期五星期六" ;
  71. whss="海中金炉中火大林木路旁土剑锋金山头火洞下水城墙土白腊金杨柳木泉中水屋上土霹雷火松柏木长流水沙中金山下火平地木壁上土金箔金佛灯火天河水大驿土钗钏金桑松木大溪水沙中土天上火石榴木大海水";
  72. g12ss="建除满平定执破危成收开闭";
  73. st28ss="角亢氐房心尾箕斗牛女虚危室壁奎娄胃昴毕觜参井鬼柳星张翼轸";
  74.  
  75. setDisplay (0);
  76. print " 请选择:输入日期 " ;
  77. bzwh ( ) ; //八字五行计算
  78. while (){}
  79. }//main ()
  80.  
  81. bzwh ( ){ //八字干支表gzs五行表 whs
  82. int n1,n2 ;
  83. tgs="甲乙丙丁戊己庚辛壬癸" ;
  84. dzs="子丑寅卯辰巳午未申酉戌亥" ;
  85. whs1="木木火火土土金金水水" ;
  86. whs2="水土木木土火火土金金土水" ;
  87. setDisplay (0);
  88. for (i=0; i<60; i++){
  89. n1=i-i/10*10 ; n2=i-i/12*12 ;
  90. s1=subString (tgs, n1, 1) ;
  91. s2=subString (dzs, n2, 1) ;
  92. s3=subString (whs1, n1, 1) ;
  93. s4=subString (whs2, n2, 1) ;
  94. gzs=gzs+s1+s2 ; //建八字表
  95. whs=whs+s3+s4 ; } //建五行表
  96. }//bzwh ()
  97.  
  98. test (){ // 生辰八字计算,测试
  99. cs.ClearDraw (0,src); //清屏
  100. clearOutput () ;
  101. cs.SetTextSize (30);
  102. cs.SetColor (255,0,0,150) ;
  103. fname="/storage/emulated/0/tutu.jpg";
  104. cs.DrawBitmap(fname,0,2); //加底图
  105. sx=60 ; sy=100 ;
  106. ss="InputDate = "+dy2+"-"+dm2+"-"+dd2;
  107. cs.DrawText (ss, sx, sy-60);
  108. print ss ;
  109. ss= "是日为:"+wds ;
  110. print ss ;
  111. cs.DrawText (ss, sx, sy-30);
  112. print " " ;
  113. print "all days = ",alln," ",alln1;
  114. // 计算节气日,年柱以立春日起算
  115. // 计算节气日,月柱以月节气日起算
  116. //**** calculate solarterm //show 节气
  117. dy2=intToString(dy); //show 节气
  118. dm2=intToString(dm);
  119. dy1=stringToDouble(dy2);
  120. dm1=stringToDouble(dm2);
  121. dy0=dy1;
  122. n=dm*2-1;
  123. caljq(); //节气计算
  124. jqd1=(int)(dd1);
  125. jqs1=subString(jname2,0,2);
  126. cs.DrawText (jname2,sx,sy+20);
  127. jqss1=jname2;
  128. n=dm*2;
  129. caljq (); //节气计算
  130. jqd2=(int)(dd1);
  131. jqs2=subString(jname2,0,2);
  132. cs.DrawText(jname2,sx,sy+50);
  133. jqss2=jname2;
  134. print jqss1 ;
  135. print jqss2 ;
  136. //calculate GZ,gzy,gzm,gzd,alln
  137. ss= "节气日 : " +intToString(jqd1) ;
  138. print ss ;
  139. cs.DrawText(ss, sx, sy+90);
  140. print " " ;
  141. print " " ;
  142. ss= "八字五行计算如下:" ;
  143. print ss ;
  144. print " " ;
  145. cs.DrawText(ss, sx, sy+150);
  146. //计算天数,dy+2096,算公元前避免出现负数
  147. alln1=alln1+dd-1; //all days
  148. n=(dy+2096);
  149. if(dm<2)n=n-1;
  150. if(dm==2&&dd<jqd1)n=n-1;
  151. gzy=n-(int)(n/60*60);
  152. s1=subString(gzs,gzy*2,2); //年柱
  153. if(dd<jqd1){mz=1;}else{mz=0;}
  154. gzn1=(dy+2096)*12+dm-mz;
  155. gzm=gzn1-(int)(gzn1/60*60);
  156. s2=subString (gzs,gzm*2,2); //月柱
  157. n1=alln1+9;
  158. gzd=n1-(int)(n1/60*60);
  159. s3=subString(gzs,gzd*2,2); //日柱
  160. gzh=(gzd-(int)(gzd/5*5))*12;
  161. s4=subString(gzs,gzh*2,2); //时柱
  162. dd2=intToString(dd); //this day $
  163. if(len(dd2)==1)dd2="0"+dd2; //format
  164. s="日期:"+dy2+" 年 "+dm2+" 月 "+dd2+ " 日";
  165. //cs.SetTextSize (27);
  166. cs.DrawText(s,sx, sy+200);
  167. print s ;
  168. bzs="八字:"+s1+" "+s2+" "+s3+" "+s4;
  169. cs.DrawText(bzs,sx , sy+230);
  170. print bzs ;
  171. string wh ;
  172. s11=subString (whs,gzy*2,2);
  173. s12=subString (whs,gzm*2,2);
  174. s13=subString (whs,gzd*2,2);
  175. s14=subString (whs,gzh*2,2);
  176. wh=s11+" "+s12+" "+s13+" "+s14 ;
  177. wh="五行:"+wh ;
  178. cs.DrawText(wh, sx, sy+260); //output
  179. print wh ;
  180. print " " ;
  181.  
  182. //八字五行十二建二十八宿
  183. s=" " ; ss=" " ;
  184. s11=subString (whss,(gzy/2)*3,3);
  185. s12=subString (whss,(gzm/2)*3,3);
  186. s13=subString (whss,(gzd/2)*3,3);
  187. s14=subString (whss,(gzh/2)*3,3);
  188. s="年 : "+s1+s11; //show 五行
  189. cs.DrawText (s,sx, sy+320);
  190. print "年: "+s1+s11 ;
  191. s="月 : "+s2+s12;
  192. cs.DrawText (s, sx, sy+350);
  193. print "月: "+s2+s12 ;
  194.  
  195. n=alln1+3; //print 二十八宿
  196. n1=n-n/28*28;
  197. s5=subString (st28ss,n1,1);
  198. cs.DrawText (ss, sx+190, sy+380);
  199. n=alln1-(dy-1900)*12-dm+10; // 12建日
  200. if (dd>=jqd1)n=n-1;
  201. n1=n-n/12*12;
  202. s6=s5+subString(g12ss,n1,1);
  203. cs.DrawText (s6, sx+200, sy+380);
  204. s="日 : "+s3+s13 ;
  205. cs.DrawText (s, sx, sy+380);
  206. print "日: "+s3+s13+s6 ;
  207. s="时 : "+s4+s14;
  208. cs.DrawText (s, sx, sy+410);
  209. print "时: "+s4+s14 ;
  210.  
  211. //** 八字起时 ,十二时辰对照表 *************
  212. x0=60;
  213. y0=600;
  214. cs.SetTextSize(24);
  215. s="起时 : ";
  216. cs.DrawText(s,x0,y0-30);
  217. s="23 - 1 11 - 13";
  218. cs.DrawText(s,x0,y0-5);
  219. s=" 1 - 3 13 - 15";
  220. cs.DrawText(s,x0,y0+20);
  221. s=" 3 - 5 15 - 17";
  222. cs.DrawText(s,x0,y0+45);
  223. s=" 5 - 7 17 - 19";
  224. cs.DrawText(s,x0,y0+70);
  225. s=" 7 - 9 19 - 21";
  226. cs.DrawText(s,x0,y0+95);
  227. s=" 9 - 11 21 - 23";
  228. cs.DrawText(s,x0,y0+120);
  229. for(i=0;i<6;i++){
  230. s5=subString(gzs,(gzh+i)*2,2);
  231. s6=subString(gzs,(gzh+6+i)*2,2);
  232. s=s5+" "+s6;
  233. cs.DrawText(s,x0+80,y0-5+i*25); }
  234. string wh1, wh2, h1, h2 ;
  235. wh1=" "; wh2=" "; h1=" "; h2=" ";
  236. n=gzh ;
  237. for(i=n ; i<n+6; i++){
  238. whs1=subString (whs, i*2, 2) ;
  239. whs2=subString (whs, (i+6)*2, 2) ;
  240. wh1=wh1+whs1+" " ;
  241. wh2=wh2+whs2+" " ;
  242. s5=subString(gzs, i*2,2);
  243. s6=subString(gzs, (i+6)*2,2);
  244. h1=h1+s5+" " ;
  245. h2=h2+s6+" " ; }
  246. wh1="23 - 11 "+wh1 ;
  247. wh2="11 - 23 "+wh2 ;
  248. cs.SetTextSize (24);
  249. print " " ;
  250. print "起时:" ;
  251. cs.DrawText (wh1,50,760) ;
  252. cs.DrawText (wh2,50,790) ;
  253. print " " ;
  254. print "23 - 11 ", h1 ;
  255. print wh1 ;
  256. print " " ;
  257. print "11 - 23 ", h2 ;
  258. print wh2 ;
  259. cs.Update () ;
  260. }//test ( )
  261.  
  262. inputDate (){ //输入日期
  263. string sDat[101];
  264. getDate(ds); //getDate = today
  265. pickDate("输入日期:",ds); //input date
  266. dy=ds[0];
  267. dm=ds[1];
  268. dd=ds[2];
  269. dy2=intToString(dy); //this year
  270. dm2=intToString(dm); //this month
  271. if (dm<10) dm2="0"+dm2 ;
  272. dd2=intToString(dd); //this day
  273. if (dd<10) dd2="0"+dd2 ;
  274. //print "InputDate = ",dy2+"-",dm2+"-"+dd2;
  275. getWeekday () ;
  276. }//inputDate()
  277.  
  278. getWeekday () {
  279.  
  280. //传人dy dm dd , 输出星期wds , 天数alln1
  281. //计算月首日星期几 alln=... +1+1 ;
  282. //计算当日或输入 是日 alln=... +1+dd ;
  283. int ty, tm ;
  284. ty=dy;
  285. tm=dm;
  286. if (dm<3){
  287. ty=dy-1;
  288. tm=dm+12; }
  289. //first day=1 this month
  290. //iWeek=(d+2*m+3*(m+1)/5+y+y/4-y/100+y/400)
  291. //mod 7 基姆拉尔森公式
  292. alln=2*tm+3*(tm+1)/5+ty+(int)(ty/4);
  293. alln=alln-(int)(ty/100)+(int)(ty/400)+1+dd;
  294. wd=alln-alln/7*7; //mod (alln,7)
  295. wds=subString(wdss,wd*3,3);
  296. string yds; //计算天数
  297. string ydds;
  298. double tms;
  299. yds="000031059090120151181212243273304334";
  300.  
  301. ydds=subString(yds,(dm-1)*3,3);
  302. tms=stringToDouble(ydds);
  303. alln1=(dy-1900)*365+((dy-1900-1)/4)+(int)(tms)+1;
  304. if ((dy-dy/4*4)==0&&dm>2)alln1=alln1+1;
  305. // return weekday = wds , alln1
  306. test () ;
  307. }//getWeekday ()
  308.  
  309. myToolBarProc(int nBtn,int nContext){
  310. if(nBtn==100){//input date
  311. setDisplay (0);
  312. inputDate ( ) ;
  313. }
  314. if(nBtn==101){//test input
  315. inputDate ( ) ;
  316. }
  317. if(nBtn==102){//关闭图板文本打印输出
  318. setDisplay (0);
  319. }
  320. if(nBtn==103){//显示图板
  321. setDisplay (1);
  322. }
  323. if(nBtn==104){//退出程序
  324. clearOutput();
  325. cs.ClearDraw (0,src);
  326. setDisplay (0);
  327. exit (0);
  328. }
  329. if(nBtn==105){//@testdraw
  330. setDisplay (1);
  331. }
  332. }//myToolBar ()
  333.  
  334. caljq(){//calculate solar ** return jname2
  335.  
  336. //传入dy0, n节气序数,输出节气时间
  337. juD=dy0*(365.2423112-0.000000000000064
  338. *(dy0-100)*(dy0-100)- 0.00000003047
  339. *(dy0-100))+15.218427*n+1721050.71301;
  340. tht=0.0003*dy0-0.372781384-0.2617913325*n;
  341. yrD=(1.945*sin(tht)-0.01206*sin(2*tht))
  342. *(1.048994-0.00002583 *dy0);
  343. sD=-0.0018*sin(2.313908653*dy0
  344. -0.439822951-3.0443*n);
  345. //'vs = juD '** 平气
  346. vs = (juD + yrD + sD); // '** 定气
  347. dalt=-15+(juD-2382148)*(juD-2382148)/41048480;
  348. //print dalt;
  349. dalt = dalt/86400;
  350. //print dalt;
  351. jd = vs - 0.5 - dalt-0.025;
  352. int gg;
  353. gg=n-(int)(n/2*2);
  354.  
  355. jdtoGD ();
  356. jqs1=subString (jqnames,(n-1)*2,2);
  357. //print "jqs1 = ",jqs1;
  358. s=jqs1+" " +jname2;
  359. //print jname2;
  360. }//caljq() ****************************
  361.  
  362. //calculate jd to GD ** return jname2 *****
  363. jdtoGD(){
  364. double a,b,c,d,e;
  365. double F;
  366. double allss;
  367. F=jd-(int)(jd);
  368. //print " ";
  369. //print " JD = ",jd;
  370. //print " 时分秒 日小数 = ",F;
  371. a=(int)(jd+0.5);
  372. b=a+1537;
  373. c=(int)((b-122.1)/365.25);
  374. d=(int)(365.25*c);
  375. e=(int)((b-d)/30.6001);
  376. dd1=b-d-(int)(30.6001*e);
  377. dm1=e-1-(int)((e/14)*12);
  378. dy1=c-4715-(int)((7+dm1)/10);
  379. //print a," ",b," ",c," ",d," ",e;
  380. dy2=intToString (dy);
  381. dm2=intToString (dm);
  382. dd2=doubleToString (dd1);
  383. if (len(dm2)==1)dm2="0"+dm2;
  384. if (dd1<10)dd2="0"+dd2;
  385. dd2=subString (dd2,0,2);
  386. //print dy2+" 年 "+dm2+" 月 "+dd2+" 日 ";
  387. if(n==24)jqdn=(int)(dd1);
  388. if (n==24&&dm1<3)jqdn=jqdn+1;
  389.  
  390. //日allss 的小数转为时分秒
  391. allss=(int)((jd-a)*86400+43200.5);
  392. //print "allss = ", allss;
  393. hh1=(int)(allss/3600);
  394. mm1=(int)((allss-hh1*3600)/60);
  395. ss1=(int)(allss-hh1*3600-mm1*60);
  396. if(ss1>=60){
  397. ss1=ss1-60;
  398. mm1=mm1+1;}
  399. if(mm1>=60){
  400. mm1=mm1-60;
  401. hh1=hh1+1;}
  402. //print "JD 转为 GD,计算结果:”;
  403. hh2=doubleToString(hh1);
  404. mm2=doubleToString(mm1);
  405. ss2=doubleToString(ss1);
  406. if(hh1<10){
  407. hh2="0"+doubleToString(hh1);}
  408. if(mm1<10){
  409. mm2="0"+doubleToString(mm1);}
  410. if(ss1<10){
  411. ss2="0"+doubleToString(ss1);}
  412. hh2=subString (hh2,0,2);
  413. mm2=subString (mm2,0,2);
  414. ss2=subString (ss2,0,2);
  415. jname1=subString(jqnames,(n-1)*2,2);
  416. //print "节气 : ",jname1;
  417. jname2=jname1+": "+dm2+"-"+dd2+" "+hh2+":"+mm2+":"+ss2;
  418. //return jname2;
  419. }//jdtoGD() **************
  420.  
  421.  
  422. //**** END ****

到此这篇关于基于C语言实现计算生辰八字五行的示例详解的文章就介绍到这了,更多相关C语言计算生辰八字五行内容请搜索w3xue以前的文章或继续浏览下面的相关文章希望大家以后多多支持w3xue!

 友情链接:直通硅谷  点职佳  北美留学生论坛

本站QQ群:前端 618073944 | Java 606181507 | Python 626812652 | C/C++ 612253063 | 微信 634508462 | 苹果 692586424 | C#/.net 182808419 | PHP 305140648 | 运维 608723728

W3xue 的所有内容仅供测试,对任何法律问题及风险不承担任何责任。通过使用本站内容随之而来的风险与本站无关。
关于我们  |  意见建议  |  捐助我们  |  报错有奖  |  广告合作、友情链接(目前9元/月)请联系QQ:27243702 沸活量
皖ICP备17017327号-2 皖公网安备34020702000426号