算法两则
一、说明
早上有同学问了个十六进制数取每字节的低四位组成一个新的数的问题,然后写了个实现代码,然后最近感觉还是需要掌握算法,所以记录一下。
说到算法又想起以前同学做毕设时帮实现的汇率套利计算程序,所以也应一起搬上来。
二、十六进制数取每字节的低四位组成一个新的数
问题:32位16进制的数据,把每个字节的后四位提取出来组成新的数;比如a=0x31303233,那么提取出的b=0x1023。
实现代码:
# include <stdio.h> # include <math.h> int main(){ int a = 0x31303233; int b = 0; int count = 0; int tmp = a; while(a && 0x10 >= 0x1){ if (count == 0){ b = a % 0x10; }else{ b = (a % 0x10) * pow(0x10,count) + b; } //printf("%d times: a=%x, b=%x\n",count,a,b); a = a >> 8; count += 1; } printf("since a is 0x%x, b is 0x%x\n\n",tmp,b); }
运行结果:
三、汇率套利
问题:手执一种货币,如何利用两种货币间的汇率差倒腾兑换,能获取到最多的钱。
实现代码:
#include<stdio.h> int main() { //程序中使下标指代对应币种 char *Name[6]={"CNY","USD","JPY","EUR","HKD","GBP"}; //各币种之间兑换利率矩阵;纵坐标是1单位,横坐标是纵坐标1单位可兑换成的单位 double Rate[6][6]={{1.0,0.1548,17.4177,0.1361,1.2008,0.1078}, {6.4585,1.0,112.4919,0.8878,7.7552,0.6962}, {0.0574,0.0089,1.0,0.0078,0.0689,0.0062}, {7.3493,1.1379,128.0076,1.0,8.8248,0.7922}, {0.8328,0.1289,14.5054,0.1133,1.0,0.0898}, {9.2774,1.4365,161.5906,1.2624,11.1400,1.0}}; //获利矩阵;纵坐标1单位转成纵坐标后再转回纵坐标原币种可得到的单位,亏损全赋为0.0 double RateEarn[6][6]={{1.0,0.0,0.0,1.00023973,1.00002624,1.00010372}, {0.0,1.0,1.00117791,1.01022762,0.0,1.0000913}, {0.0,1.00117791,1.0,0.0,0.0,1.00186172}, {1.00023973,1.01022762,0.0,1.0,0.0,1.00007328}, {1.00002624,0.0,0.0,0.0,1.0,1.000372}, {1.00010372,1.0000913,1.00186172,1.00007328,1.000372,1.0}}; //Step----用于存放最优路径 //StepAccept----用于在放每步的资产 //FinalAsset----用于在放最终的资产 int Step[6]; double StepAsset[6]; double FinalAsset; int best,i,j,flag; while(true){ //每次重新初始化Step和FinalAsset for(i=0;i<6;i++){ Step[i]=0; } FinalAsset=1.0; //接收用户选择的最初币种 printf("--------------------------------------------------------------------------------\n" "0.CNY\t1.USD\t2.JPY\t3.EUR\t4.HKD\t5.GBP\t6.exit\n" "please enter your choice:"); scanf("%d",&flag); printf("\n"); if(flag>5) { return 0; } Step[0]=flag; //步长从1到5 for(int StepLength=1;StepLength<6;StepLength++){ //每次循环前都要将组初始化,以使数组能用于下一步长 for(i=0;i<6;i++){ StepAsset[i]=0.0; } //筛选可能路径 for(int Target=0;Target<6;Target++){ if(Step[StepLength-1]!=Target){ if((RateEarn[Step[StepLength-1]][Target]>=1.0)&&(RateEarn[Target][flag]>=1.0)) { StepAsset[Target]=FinalAsset*Rate[Step[StepLength-1]][Target]*Rate[Target][flag]; } } } //在可能路径中选出最优路径 best=0; for(i=1;i<6;i++){ if(StepAsset[best]<StepAsset[i]){ best=i; } } Step[StepLength]=best; FinalAsset=FinalAsset*Rate[Step[StepLength-1]][best]; //以下代码用于代码输出本步长最后结果 printf("while StepLength is %d,the best path is:\t",StepLength); for(j=0;j<=StepLength;j++){ printf("%s->",Name[Step[j]]); } printf("%.8lf",FinalAsset*Rate[Step[StepLength]][flag]); switch(flag){ case 0: printf("CNY"); break; case 1: printf("USD"); break; case 2: printf("JPY"); break; case 3: printf("EUR"); break; case 4: printf("HKD"); break; case 5: printf("GBP"); break; } printf("\n\n"); } printf("--------------------------------------------------------------------------------\n"); } return 0; }
实现效果: