/* 问题:输入N个学生的信息,进行查询 输入: 4 01 李江 男 21 02 刘唐 男 23 03 张军 男 19 04 王娜 女 19 5 02 03 01 04 03 输出: 02 刘唐 男 23 03 张军 男 19 01 李江 男 21 04 王娜 女 19 03 张军 男 19 N;学生个数,<=1000, M,查询M次,M<=10000 时间复杂度: 普通搜索:O(n*m) = O(1000*10000)=O(10000000),千万数量级 二分搜索:以学号为搜索主题,O(log2N*M)(搜索) + O(log2N*N)(排序) =O(10*10000) + O(10*1000)=O(100000),十万级 关键: 1 二分查找的查询条件 是 while(low <= high),=号不能丢掉,因为有时候low = high时,才找到目标值 2 使用二分查找的前提条件是,有序排列,为此可以使用快速排序进行排序(你没有做) 3 性别虽然是一个汉字,但是至少需要2个字节,因此存储类型必须用字符指针 */ #include <stdio.h> #include <stdlib.h> typedef struct StuInfo { bool operator < (StuInfo& stuInfo) { return _iStuNo < stuInfo._iStuNo; } int _iStuNo; char _sName[32]; char _sSex[6];//关键性别如果是汉字,至少2个字节,但是char只有1个字节 int _iAge; }StuInfo; template<typename T> int partition(T* A,int low ,int high) { T iPos = A[low]; while(low < high) { while(low < high && iPos < A[high]) { high--; } A[low] = A[high]; while(low < high && A[low] < iPos) { low++; } A[high] = A[low]; } A[low] = iPos; return low; } template<typename T> void quickSort(T *A,int low,int high) { if(low < high) { int iPos = partition(A,low,high); quickSort(A,low,iPos - 1); quickSort(A,iPos + 1,high); } } //int binarySearch(int *Array,int iLow,int iHigh,int iSeaValue) int binarySearch(int *Array,int iLow,int iHigh,int iSeaValue) { int iMid; while(iLow <= iHigh)//易错,这边要加等号,否则low=high不循环了 { iMid = (iLow + iHigh)/2; if(iSeaValue < Array[iMid]) { iHigh = iMid - 1; } else if(iSeaValue > Array[iMid]) { iLow = iMid + 1; } else { return iMid; } } //程序走到这里,表示没有找到 return -1; } int main(int argc,char* argv[]) { int N; //while(EOF!=scanf("%d %s %c %d",&stuInfo.iStuNo,stuInfo.sName,stuInfo.cSex,stuInfo.iAge)) while(EOF!=scanf("%d",&N) && N <= 1000) { StuInfo stuInfo[100]; int iGivStuNo[100],i; //输入N个学生的信息 for(i = 0; i < N ;i++) { scanf("%d %s %s %d",&stuInfo[i]._iStuNo,stuInfo[i]._sName,stuInfo[i]._sSex,&stuInfo[i]._iAge);//字符串不需要取地址符,字符需要取地址符,又是取地址符没加 //iGivStuNo[i] = stuInfo[i]._iStuNo; //printf("\n"); } //对输入的学生信息按照学号进行快速排序 quickSort<StuInfo>(stuInfo,0,N-1); //将已经排好序的学号存入数组 for(i = 0; i < N ;i++) { iGivStuNo[i] = stuInfo[i]._iStuNo; } int M; scanf("%d",&M); if(M > 10000) { break; } else { int iStuNoArr[100]; int iStuNo,j; for(j = 0;j < M;j++) { scanf("%d",&iStuNo); iStuNoArr[j] = iStuNo; } //下面用二分法进行查找 for(j = 0; j < M ; j++) { int iRes = binarySearch(iGivStuNo,0,N-1,iStuNoArr[j]); if(iRes==-1) { printf("%s","No Answer!"); } else { printf("%d %s %s %d\n",stuInfo[iRes]._iStuNo,stuInfo[iRes]._sName,stuInfo[iRes]._sSex,stuInfo[iRes]._iAge); } } } } system("pause"); getchar(); return 0; }