#include<iostream> #include<math.h> #include<string.h> using namespace std; //奶牛生子:一只幼年奶牛第4年可生下第一只奶牛 以后每年生一只 //现有一只幼年奶牛 20年后 共有多少只奶牛 int CowNum(int size) { int* year = new int[size]; memset(year, 0, size*sizeof(int)); year[0] = 1; int count = 0; for (int i = 0; i < size; ++i) { if (i >= 4-1 ) { year[i] = year[i - 1] + year[i - 3]; } } for (int i = 0; i < size; ++i) count += year[i]; return count; delete year; } int CowNum1(int year) { int newCow1 = 1;//1岁 牛 开始有1只 int newCow2 = 0;//2岁 牛 int newCow3 = 0;//三岁 牛 int newCow4 = 0;//四岁 牛 成年牛 //int newCow5 = 0;//将题意理解成第5年牛开始生 则加个5岁牛数量 int oldCow = 0;//可生崽 牛 int count = 0; //总数 for (int yearcnt = 2; yearcnt <= year; ++yearcnt)//默认牛是1岁 第一次进去牛 2岁 { //newCow5 = newCow4; newCow4 = newCow3; //3岁牛长 4岁 oldCow += newCow4; newCow3 = newCow2; newCow2 = newCow1;//一岁牛 长2岁 newCow1 = oldCow;//1岁牛 为可生崽牛 的数量 count = oldCow + newCow1+newCow2+newCow3;//总数为 成年牛 + 1 2 3岁牛 //count = oldCow + newCow1 + newCow2 + newCow3+newCow4; //如果是5岁开始生 //总数为 成年牛 + 1 2 3 4岁牛 } return count; } //一串珠子 有M<=10种颜色 n颗 求最小的含所有颜色的子串 //逻辑复杂的一道题 void AllColorBead(char* bead, int colorNum)//bead 珠子串 colorNum 颜色数 { char* head,* str=bead; //head 最短子串头 str 循环变量 int clrNum = 0 ,beadCnt=0,tmpCnt=1000000,tmpClrNum=-1; char colorArr[128] = { 0 };//用来判断每种颜色是否第一次出现 来区分颜色数是否+1 while (*str!=‘\0‘) { if (*(str + 1) != *str) //如果相连的颜色一样直接跳过 { char* tmp = str; //记录str 如果该子串满足要求 head=str while ((*tmp)!=‘\0‘) { if (colorArr[*tmp] == 0)//颜色第一次出现 clrNum++ { ++clrNum; ++colorArr[*tmp]; } //if (clrNum == colorNum) //告诉珠子颜色数逻辑 //{ // if (tmpCnt > beadCnt)//如果该子串满足要求 head = str 跳出循环 // { // tmpCnt = beadCnt; // head = str; // } // break; //} if (tmpClrNum==clrNum)//不告诉珠子颜色数 第一次需完全遍历 求出颜色数 break; ++beadCnt; ++tmp; } if (tmpCnt > beadCnt&&clrNum>=tmpClrNum)//如果该子串满足要求 head = str 跳出循环 { tmpCnt = beadCnt; tmpClrNum = clrNum;//不告诉珠子颜色数需加条件 head = str; } clrNum = 0; //每次检索子串结束 计数器制零 beadCnt = 0; memset(colorArr, 0, 128 * sizeof(char)); } str++; //跳刀下一个子串 } for (int i = 0; i <= tmpCnt; ++i)//输出子串 cout << *(head + i); cout << endl; } //n*n的 回字形 蛇形 数组 按行输出 // eg: n=3 // 1 2 3 // 8 9 4 // 7 6 5 void SnakeArr(int n) { int* arr = new int[n*n]; //储存数组 int type = 0;//写入数组类型 0 从左向右 1 从上往下 2 从右往左 3从下往上 int num = 1;//输入数组值 1---n*n int gap = 0;//每行输出跨度 int i = 0, j = 0;//数组下标 while (num <= n*n)//num自加到n*n时说明 全填满了 结束循环 { if (type == 0)//从左向右 写入数组 { for (int index = i + gap; i < n - gap&&num <= n*n; ++i) arr[i+j*n] = num++; ++type;//横行写入数组完成 类型+1 变竖行 ++j;//j+1到下一行 } if (type ==1)//从上到下 { --i;//i退到 最外层处 for (int index = j + gap; j< n - gap&&num <= n*n; ++j) arr[i + j*n] = num++; ++type; --i; //i退到最外层-1处 } if (type == 2)//从右到左 { --j;//j退到未写入最外层 for (int index = i - gap; i >= gap&&num <= n*n; --i) arr[i + j*n] = num++; ++type; ++i;//i到左边未遍历最外层 } if (type == 3)//从下道上 { --j;//j退到未写入最外层 for (int index = n - gap; j > gap&&num <= n*n; --j) arr[i + j*n] = num++; ++j;//j退到未写入最外层 ++i;//i到左边未遍历最外层 type = 0;//写入方向 类型 重新置1 } gap++;//四个方向 都写入完成 跨度+1 } for (int index = 0; index < n*n; ++index) cout << arr[index] << ‘ ‘; cout << endl; delete arr; } //在一个字符串中 删除多余字符后 找到最长的 回文字符串长度 //eg:abbedbba 结果 abbebba //逻辑庞大 十分复杂 网上好像有高端算法 int PlalindromeNum(char* str,int start,int end) { if (*str == 0)//判断 指针有效性 return 0; int count = 0;//当前回文字符串的字符数 int bigCnt = 1;//最大回文字符串字符数 int right = end;//临界值 while (start<end&&count!=2)//如果找到最后一个当前字符的匹配项 或者 字符串到尾 跳出循环 { //start 与end为当前子串最两端一对相同字符 for (int i = start + 1; i <=right; ++i) { if (str[i] == str[start]) { end = i; count = 2;//有相同项 count为2 } } if (count != 2)//没有相同项 跳到下个字符 ++start; } if (end - start>2)//递归 找一对相同字符中的其他相同字符数量 count += PlalindromeNum(str, start + 1, end - 1); else if (end - start == 2)//当end-start相距为2 说明中间包含若干单独字符 count++ { ++count; } if (right -end>1)//如果临界值-end>1说明后面还有没有遍历的字符 { if (bigCnt < count)//则将count 保存 置0 bigCnt = count; count = 0; count += PlalindromeNum(str, end+1 , right);//从子串开始继续递归找匹配字符 } if (bigCnt < count) bigCnt = count;//始终保持bigCnt为最长回文子串的字符数 return bigCnt; } ////用递归实现n位的格雷码 //至今未想明白 // //char* Gray(int n) //{ // char *arry = (char*)malloc(sizeof(char)*(int)pow(2, n)+1); // if (n =1) // { // arry[0] = ‘0‘; // arry[1] = ‘1‘; // arry[2] =0 ; // return arry ; // } // // char * tmp=Gray(n - 1); // int j = (int)pow(2, n) - 2; // for (int i = 0;i<j; ++i) // { // arry[i] = tmp[i] + 0; // arry[j - 1 - i] = tmp[i] + 1; // } // return arry; //} // //有一串珠子2种颜色(红,蓝),n个(n为奇数),有多少个蓝珠子才能确定无论什么顺序穿 //都能从不同位置的两个蓝珠子 //截断为2串,并得到一串数量为(n+1)/2(不包括这两个蓝色珠子) //重在逻辑理解 代码简单 void pearl_num(int n) { if (n < 3 || n % 2 != 1) return; int head = 0,end=0,count=0,num=2; for (int i = 1; i <n-2; ) { end = i; if (end == (n + 1) / 2) { printf("%d\n", num); return; } if ((end - head - 1) == (n + 1) / 2 || (n - 1 - end) == (n + 1) / 2) { i++; } else if (count > 0) { count--; i++; } else { num++; count=num-2; i = 1; } } printf("无答案!\n"); } //数字的汉子读法 0<=num<1000 例如 输入 101 输出yibailingyi void test() { int num = 0; char* a[12] = { "ling", "yi", "er", "san", "si", "wu", "liu", "qi", "ba", "jiu", "shi", "bai" }; while (1) { int arr[3] = { 0 }; char* pinyin = ((char*)malloc(sizeof(char)*20)); scanf("%d", &num); int tmp1 = num; for (int i = 2; i >= 0; --i) { arr[i] = num % 10; num /= 10; } char* tmp = pinyin; for (int i = 0; i<3; ++i) { if (tmp1 == 0) { strcpy(pinyin, "ling\0"); pinyin += 4; break; } if (i == 0) { if (arr[i] != 0) { strcpy(pinyin, a[arr[i]]); pinyin += (int)strlen(a[arr[i]]); strcpy(pinyin, a[11]); pinyin += 3; } } else if (i == 1) { if (arr[i] == 0) { if (arr[i - 1] == 0) continue; if (arr[i + 1] == 0) break; strcpy(pinyin, a[0]); pinyin += 4; } else { strcpy(pinyin, a[arr[i]]); pinyin += (int)strlen(a[arr[i]]); strcpy(pinyin, a[10]); pinyin += 3; } } else { if (arr[i] != 0) { strcpy(pinyin, a[arr[i]]); pinyin += (int)strlen(a[arr[i]]); } } free(pinyin); } *pinyin = 0; printf("%s\n", tmp); pinyin = tmp; } } //小明装装备按从左到右装 如果物品太大 (大于背包最大容量)直接丢弃,如果背包装不下 //换下个背包,前一个背包不再用,小明能装多少物品? //n 物品数 t 背包负重 m 背包个数 //a[0]--a[n]被给物品质量 // void package() { int m, t ,n; int a[20] = { 0 }; int i = 0; scanf("%d%d%d",&n,&t,&m); while (i < n) { scanf("%d", &a[i++]); } int count = 0, tmp = t; for (i=0; m>0 && n > 0;) { if (a[i] > tmp) { i++; n++; } else if (t-a[i]>=0) { t -= a[i++]; ++count; --n; } else if (m>1) { --m; t = tmp; t -= a[i++]; ++count; --n; } else { ++i; --n; } } printf("%d\n",count); } //将字符串 按空格 翻转 同时 将大小写互换 例:“this Is a Str”-> "sTR A iS THIS" //默认给定字符串只含有字母与空格 void reverse_str_A(char * src) { char* str = (char*)malloc(sizeof(char)*(strlen(src)));//将给定字符串拷贝到可写字符数组中 strcpy(str,src); char* tmp = str; int i = 0; char* out = (char*)malloc(sizeof(char)*(strlen(str) ));//生成储存处理后的字符数组 char* output = out; while (*(tmp))//计算空格个数 { if (*tmp++ == ‘ ‘&&*tmp!=0)//‘\0‘之前的不计算 ++i; } int count = i; int *a = (int *)malloc(sizeof(int)*i);//生成记录空格下标的数组 tmp = str; i = 0; int j = 0; while (*tmp)//将空格下标记录并替换为‘\0‘方便拷贝 { if (*tmp == ‘ ‘)// { *tmp = 0; if (*(tmp + 1)== 0)//‘\0‘之前的空格直接处理 将输出数组第一个字符替换为空格 并指向下一个 { *output = ‘ ‘; output++; break; } a[j++] = i; } ++tmp; ++i; } tmp = str; for ( j = count-1; j>=0; --j)//将分割的字符串从后向前依次写入输出字符串并将各自\0替换为空格 { if (a[0] == 0&&j==0) break; strcpy(output,tmp+a[j]+1); output += strlen(tmp + a[j]+1); *(output++) = ‘ ‘; } if (a[0] == 0)//处理开始空格 tmp++; strcpy(output, tmp );//将首字符串拷贝到尾 output += strlen(tmp ); if (a[0] == 0)//将开始的空格移到末尾 { output[0]= ‘ ‘; output[1] = 0; } i = 0; output = out; while (*(output+i))//依次替换大小写 { if (*(output + i) >= ‘a‘&&*(output + i) <= ‘z‘) *(output + i) -= 32; else if (*(output + i) >= ‘A‘&&*(output + i) <= ‘Z‘) *(output + i) += 32; ++i; } cout << out <<"***********"<< endl;//输出 free(out); free(output); free(a); } int main() { cout<<CowNum(20)<<endl; cout << CowNum1(20) << endl; AllColorBead("11231324566457711234567111", 7); AllColorBead("asdccaacsdfdgfwererdfg",8); SnakeArr(5); char* a = "vvaabbcdcbbaaxaabbcdcbbaax"; cout << PlalindromeNum(a, 0, strlen(a)) << endl; /*pearl_num(101); package();*/ reverse_str_A(" This w W w Is str "); /*test();*/ /*char * aa; aa=Gray(10); cout << aa << endl;*/ return 0; }
时间: 2024-10-13 09:58:00