华为上机题汇总(五)
来源:互联网 发布:google 算法面试题 编辑:程序博客网 时间:2024/05/22 00:13
华为上机题汇总(五)
注:编译环境为Visual Studio 2012,答案仅供参考。
目录
- 华为上机题汇总五
- 目录
- 第二十一题
- 第二十二题
- 第二十三题
- 第二十四题
- 第二十五题
第二十一题
21.通过键盘输入100以内正整数的加、减运算式,请编写一个程序输出运算结果字符串。
输入字符串的格式为:“操作数1 运算符 操作数2”,“操作数”与“运算符”之间以一个空格隔开。
补充说明:
1. 操作数为正整数,不需要考虑计算结果溢出的情况。
2. 若输入算式格式错误,输出结果为“0”。
示例
输入:“4 + 7” 输出:“11”
输入:“4 - 7” 输出:“-3”
输入:“9 ++ 7” 输出:“0” 注:格式错误
#include <iostream>#include <string>#include <vector>using namespace std;bool isNumber(const string &s , int &num){ int sum = 0; for (auto begin = s.rbegin();begin != s.rend();begin++) { if (*begin < '0' || *begin > '9') { return false; } sum += (*begin - '0') * pow(10,begin - s.rbegin()); } num = sum; return true;}int caculate(const string &s){ if (s.empty()) return 0; auto begin = s.begin(); vector<string> v; while (begin != s.end()) { auto ahead = begin + 1; while (ahead != s.end() && *ahead != ' ') { ahead++; } string tmp(begin,ahead); v.push_back(tmp); if (ahead != s.end()) ahead++; begin = ahead; } if (v.size() != 3) return 0; int num1,num2; if (!isNumber(v[0],num1) || !isNumber(v[2],num2) || v[1].size() != 1) return 0; if (v[1] == "+") { return num1 + num2; } else if (v[1] == "-") { return num1 - num2; } return 0;}int main(){ string input; getline(cin,input); cout << caculate(input) << endl; return 0;}
第二十二题
22.IP地址匹配(60分)
问题描述:
在路由器中,一般来说转发模块采用最大前缀匹配原则进行目的端口查找,具体如下:
IP地址和子网地址匹配:
IP地址和子网地址所带掩码做AND运算后,得到的值与子网地址相同,则该IP地址与该子网匹配。
比如:
IP地址:192.168.1.100
子网:192.168.1.0/255.255.255.0,其中192.168.1.0是子网地址,255.255.255.0是子网掩码。
192.168.1.100&255.255.255.0 = 192.168.1.0,则该IP和子网192.168.1.0匹配
IP地址:192.168.1.100
子网:192.168.1.128/255.255.255.192
192.168.1.100&255.255.255.192 = 192.168.1.64,则该IP和子网192.168.1.128不匹配
最大前缀匹配:
任何一个IPv4地址都可以看作一个32bit的二进制数,比如192.168.1.100可以表示为:11000000.10101000.00000001.01100100,
192.168.1.0可以表示为11000000.10101000.00000001.00000000
最大前缀匹配要求IP地址同子网地址匹配的基础上,二进制位从左到右完全匹配的位数尽量多(从左到右子网地址最长)。比如:
IP地址192.168.1.100,同时匹配子网192.168.1.0/255.255.255.0和子网192.168.1.64/255.255.255.192,
但对于子网192.168.1.64/255.255.255.192,匹配位数达到26位,多于子网192.168.1.0/255.255.255.0的24位,
因此192.168.1.100最大前缀匹配子网是192.168.1.64/255.255.255.192。
请编程实现上述最大前缀匹配算法。
要求实现函数:
void max_prefix_match(const char *ip_addr, const char *net_addr_array[], int *n)
【输入】ip_addr:IP地址字符串,严格保证是合法IPv4地址形式的字符串
net_addr_array:子网地址列表,每一个字符串代表一个子网,包括子网地址和掩码,
表现形式如上述,子网地址和子网掩码用’/’分开,严格保证是
合法形式的字符串;如果读到空字符串,表示子网地址列表结束
【输出】n:最大前缀匹配子网在*net_addr_array[]数组中对应的下标值。如果没有匹配返回-1
示例
输入:
ip_addr = “192.168.1.100”
net_addr_array[] =
{
“192.168.1.128/255.255.255.192”,
“192.168.1.0/255.255.255.0”,
“192.168.1.64/255.255.255.192”,
“0.0.0.0/0.0.0.0”,
“”
}
输出:n = 2
#include <iostream>#include <string>#include <vector>using namespace std;void convert(const char *ip,vector<int> &v){ const char *begin = ip, *ahead; while (*begin != '\0') { ahead = begin + 1; while (*ahead != '\0' && *ahead != '.' && *ahead != '/') { ahead++; } string tmp(begin,ahead); v.push_back(stoi(tmp)); if (*ahead == '\0') break; begin = ++ahead; }}int match(const char *ip, const char *net){ vector<int> vIp; vector<int> vNet; convert(ip,vIp); convert(net,vNet); for (int i = 0; i < 4; i++) { int tmp = vIp[i] & vNet[4+i]; if (tmp != vNet[i]) { return -1; } } int matchByte = 0; for (int i = 0; i < 4; i++) { if (vIp[i] == vNet[i]) { matchByte += 8; continue; } int tmp = vIp[i] ^ vNet[i]; int index = 0; for (int i = 7; i > 0; i--) { if (tmp & 1) { index = i; } tmp >>= 1; } matchByte += index; break; } return matchByte;}void max_prefix_match(const char *ip_addr, const char *net_addr_array[], int *n){ int index = 0, maxIndex = -1, maxByte = -1; while (*net_addr_array != "") { int matchByte = match(ip_addr,*net_addr_array++); if (matchByte > maxByte) { maxIndex = index; maxByte = matchByte; } index++; } *n = maxIndex;}int main(){ const char * ip_addr = "192.168.1.100"; const char * net_addr_array[] = {"192.168.1.128/255.255.255.192", "192.168.1.0/255.255.255.0", "192.168.1.64/255.255.255.192", "0.0.0.0/0.0.0.0", ""}; int n = 0; max_prefix_match(ip_addr,net_addr_array,&n); cout << n << endl; return 0;}
第二十三题
23.编写一个程序,实现排序算法,从小到大输出,数字间以逗号分隔,所有数字为非负整数。数目小于1028;
输入:1,6,3,5
输出:1,3,5,6
#include <iostream>#include <string>#include <vector>#include <algorithm>using namespace std;void sortStr(const string &input, string &output){ vector<int> v; auto begin = input.begin(); while (begin != input.end()) { auto ahead = begin + 1; while (ahead != input.end() && *ahead != ',') { ahead++; } string tmp(begin,ahead); v.push_back(stoi(tmp)); if (ahead == input.end()) break; begin = ++ahead; } sort(v.begin(),v.end()); auto vbegin = v.begin(); while (vbegin != v.end()) { output += to_string(*vbegin++); if (vbegin != v.end()) { output.push_back(','); } }}int main(){ string input,output; getline(cin,input); sortStr(input,output); cout << output << endl; return 0;}
第二十四题
24.我们把只包含因子2,3,5的数称为丑数,把1当作第一个丑数,求从小到大的第n个丑数
输入:1都500之间的整数(包含1和500)
输出:第n个丑数。不在1-500输出-1
#include <iostream>#include <vector>using namespace std;int min(int a, int b , int c){ int tmp = a < b ? a : b; return tmp < c ? tmp : c;}int findArglyNum(int n){ if (n < 1 || n >500) { return -1; } vector<int> v(n,1); int pos2 = 0, pos3 = 0, pos5 = 0; for (int i = 1; i < n; i++) { v[i] = min(2*v[pos2],3*v[pos3],5*v[pos5]); if (v[i] == 2*v[pos2]) { pos2++; } if (v[i] == 3*v[pos3]) { pos3++; } if (v[i] == 5*v[pos5]) { pos5++; } } return v[n-1];}int main(){ int n; cin >> n; cout << findArglyNum(n) << endl; return 0;}
第二十五题
N个城市(N<=10),从0到9编号,城市间要么有路,要么没路,计算城市A到B之间到底有多少条路。
输入:N A B(1<N<=10,0<=A,B<=9)
A为出发城市,B为目的城市。然后n行表示行编号的城市到其他城市有没有路,0表示没有,1表示有路。
输出:A到B有多少条路
输入:3 0 2
1 1 1
1 1 1
1 1 1
输出:2
#include <iostream>#include <vector>using namespace std;bool canVisit(int index, vector<int> hasVisited){ for (auto begin = hasVisited.begin();begin != hasVisited.end();begin++) { if (index == *begin) { return false; } } return true;}int findWay(int start, int end, int n, vector<int> hasVisited, vector<vector<int>> road){ if (start == end) { return 1; } int sum = 0; vector<int> v = road[start]; for (int i = 0; i < n; i++) { if (!v[i]) continue; if (canVisit(i,hasVisited)) { hasVisited.push_back(i); sum += findWay(i,end,n,hasVisited,road); } } return sum;}int main(){ int n, a, b; cin >> n >> a >> b; vector<vector<int>> road; for (int i = 0; i < n; i++) { vector<int> v; for (int j = 0; j < n; j++) { int x; cin >> x; v.push_back(x); } road.push_back(v); } vector<int> hasVisited; hasVisited.push_back(a); cout << findWay(a,b,n,hasVisited,road) << endl; return 0;}
- 华为上机题汇总(五)
- 华为上机题汇总
- 华为上机题汇总(一)
- 华为上机题汇总(二)
- 华为上机题汇总(三)
- 华为上机题汇总(四)
- 华为上机题汇总(六)
- 华为上机题汇总(七)
- 华为上机题汇总(八)
- 华为上机题汇总(九)
- 华为上机题汇总(十)
- 华为上机题汇总(十一)
- 华为上机题汇总(十二)
- 华为上机题汇总(十三)
- 华为上机题汇总(十四)
- 华为上机题汇总(十五)
- 华为上机题汇总(十六)
- 华为上机题汇总(十七)
- JQuery处理绑定多个button事件
- Sweet Alert Dialog
- "C语言之美" -- 变量名
- jsp中引用的jstl 和fmt标签
- Math.round这个方法有坑
- 华为上机题汇总(五)
- AngularJS动态加载模块和依赖
- Android注解框架butterknife基本用法
- 【Leetcode】61. Rotate List - 循环链表
- 网易游戏开发软件笔试题1
- BZOJ4668 冷战
- WebService工作学习心得
- SpringMVC+Spring+Mybatis整合配置文件小记
- java Unicode编码转换为汉字