此题中将 0翻译为‘a’…25翻译为’z’ ,计算给定数字有多少种翻译方式。
思路:从第一位开始可以走一步,也可以走两步,使用递归解决,非常清晰,美中不足的是这样递归中会出现重复计算。
/** *Copyright @ 2019 Zhang Peng. All Right Reserved. *Filename: *Author: Zhang Peng *Date: *Version: *Description: **/ #include<iostream> #include<string> using namespace std; int coutnum(string & number) { //剑指offer书上的 int length = number.length(); int * counts = new int[length]; int count = 0; for (int i = length - 1; i >= 0; --i) { count = 0; if (i < length - 1) count = counts[i + 1]; else count = 1; if (i < length - 1) { int digit1 = number[i] - '0'; int digit2 = number[i + 1] - '0'; int converted = digit1 * 10 + digit2; if (converted >= 10 && converted <= 25) { if (i < length - 2) count += counts[i + 2]; else count += 1; } } counts[i] = count; } count = counts[0]; delete[] counts; return count; } int check(string & number) { int num = 10 *(number[0]-'0') + (number[1]-'0'); if (num >= 10 && num <= 25) return 1; else return 0; } int coutnum2(string & number) { //递归 int num_size = number.size(); if (num_size == 1) return 1; else if(num_size == 2) { int num = 10 * (number[0] - '0') + (number[1] - '0'); if (num >= 10 && num <= 25) return 2; else return 1; } else { string str1 = number.substr(1, num_size - 1); string str2 = number.substr(2, num_size - 2); string str3 = number.substr(0,2); //需检查是否符合要求 /*cout << num_size << endl; cout << str1 << " " << str2 << " " << str3 << endl;*/ return coutnum2(str1) + coutnum2(str2)*check(str3); } } int translator(int number) { if (number < 0) return 0; string numstr = to_string(number); return coutnum(numstr); } int translator2(int number) { if (number < 0) return 0; string numstr = to_string(number); return coutnum2(numstr); } int main() { cout << translator(12) << endl; cout << translator2(12) << endl; system("pause"); return 0; }运行结果如图: 增加非递归实现如下:
int coutnum3(string & number) { //非递归 int len = number.size(); if (len == 0) return 0; int result = 0; vector<int> count(len, 0); for (int i = len - 1; i >= 0; i--) { if (i == len - 1) count[i] = 1; else { count[i] = count[i + 1]; //默认count[i] = count[i + 1] 如果i 和i+1能翻译成字符串,则需要加上特殊的处理 string str = number.substr(i, 2); if (check(str) )//需检查是否符合要求 { if (i + 2 < len) count[i] += count[i + 2]; //i后第二位有数字,需加上count[i+2] else count[i] += 1; //i后第二位无数字,只需要加上1,即i i+1这两个字符翻译的组合 } } } result = count[0]; return result; }