君正笔试题:有八个硬币,有一个是假的,用天平量,不知道假的比真的重还是轻,请问:最少需要多少次,才能判断出假的,跟轻重。请用C代码实现。
有八个硬币,有一个是假的,用天平量,不知道假的比真的重还是轻,请问:最少需要多少次,才能判断出假的,跟轻重。请用C代码实现。
能想到方法 但是用c代码来不会实现啊。
拿六个硬币,一边放三个,
如果天平平衡,那再称剩下两个,一边放一个,
如果天平不平衡,取一边称上的三个,从中拿两个再一边放一个,如果平衡,没称那个就是假的,如果不平衡,那就一个假的咯
[解决办法]
去周磊博客找下 和去年的一题面试题一样的
[解决办法]
去年那题好像是称8个小球的
[解决办法]
#include<stdio.h>#include<conio.h>#include<time.h>#include<stdlib.h>int Fake(int A[],int l,int r,int ×);//输出假币int Weight(int A[],int l,int r);//累加l到r的和int HaveFakeCoin(int A[],int l,int r,int ×);//判断l到r有没有假币int JudgeTwo(int A[],int l,int r,int ×);//就剩连个元素时,找出假币int JudgeThree(int A[],int l,int r,int ×);//剩余三个元素int times=0;bool weight=false;//保存检测出的假币硬币是还是重int length=0;void main(){ int times=0; int A[500]; int n=0; int pos=0; srand((long)time(NULL)); do { printf("请输入金币的个数:\n"); scanf("%d",&n); length=n; for(int i=0;i<n;i++) { A[i]=0; } printf("请输入假币的位置:\n"); scanf("%d",&pos); int rands=0; rands=rand()%2; if(rands==0) { A[pos-1]=-1; } else { A[pos-1]=1; } for(i=0;i<n;i++) { printf("%d ",A[i]); } printf("\n"); printf("假币的在第%d个位置\n",Fake(A,0,n-1,times)+1);//寻找假币的位置 if(weight) { printf("比真币重:\n"); } else { printf("比真币轻:\n"); } printf("总共比较了%d次\n",times); printf("\n\n\n\n\n\n\n\t\t\t按任意键继续\n"); getch(); times=0; system("cls"); }while(true);}int Fake(int A[],int l,int r,int ×){ int mid=0; int remainder=0; do { mid=(l+r)/2; remainder=(l+r)%2; if(remainder==1)//偶数s { int result=0; if(r==(l+1)) { return JudgeTwo(A,l,r,times); } result=HaveFakeCoin(A,l,mid,times); if(result==-1)//如果左边有假币 { r=mid; } else { if(result==1)//如果假币在右边 { l=mid+1; } else//已经有假币的位置 { if(A[result]<A[result+1]) { weight=false;//轻 } else { weight=true;//重 } return result; } } } else //奇数 { // printf("l=%d,mid=%d,r=%d\n",l,mid,r); if(Weight(A,l,mid-1)==Weight(A,mid+1,r)) //如果左边和右边相同,那么假币就是中间这个 { printf("到了"); printf("times=%d",times); times++; if(A[mid]>A[l]) { weight=true; } else { weight=false; } return mid; } else { if(r==(mid+1)) { return JudgeThree(A,l,r,times); } int result=HaveFakeCoin(A,l,mid-1,times); if(result==-1)//左边 { r=mid-1; } else { if(result==1)//右边 { l=mid+1; } else { if(A[result]<A[result+1]) { weight=false;//轻 } else { weight=true;//重 } return result;//在这边已找到假币 } } } } }while(true); return 0;}int Weight(int A[],int l,int r){ int sum=0; for(int i=l;i<=r;i++) { sum+=A[i]; } return sum;}int HaveFakeCoin(int A[],int l,int r,int ×){ int mid=(l+r)/2; int remainder=(l+r)%2; if(remainder%2==1)//如果为偶数个 { times++; if(Weight(A,l,mid)==Weight(A,mid+1,r))//如果两遍相同表示这边没有假币币, //也就是这边都是真币 { return 1; } else { return -1; } } else //如果为奇数个 { times++; if(Weight(A,l,mid-1)==Weight(A,mid+1,r))//如果左边和右边相同,则可能在中间 { times++; if(A[mid-1]==A[mid])//如果中间和左边的相同,则这边没有假币 { return 1; } else //中间的就是假币 { return mid; } } else { return -1; } }}int JudgeTwo(int A[],int l,int r,int ×){ times++; if(A[l]==A[(l+2)%length])//如果左边的和其他的元素相同,则右边一个是假币 { if(A[l]<A[r]) { weight=true;//重 } else { weight=false;//轻 } return r; } else//否则左边的是假币 { if(A[l]<A[r]) { weight=false;//重 } else { weight=true;//轻 } return l; } return -2;}int JudgeThree(int A[],int l,int r,int ×){ times++; int mid=(l+r)/2; if(A[l]==A[r])//假币就在中间 { if(A[mid]>A[l]) { weight=true; } else { weight=false; } return mid; } else { times++; if(A[l]==A[mid])//假币在右边 { if(A[r]>A[mid]) { weight=true; } else { weight=false; } return r; } else//假币在左边 { if(A[l]<A[mid]) { weight=false; } else { weight=true; } return l; } } return -3;}