题目参考:
牛客网 vivo2020届春季校园招聘在线编程考试题

一根烟,一壶酒,一道算法编一宿。。。
这是个明显的图结构,九个结点,任意两个节点间相连,我们可以求出图的所有所有满足如下要求的有序路径:
1.路径长度在区间[m,n]内
2.路径经过的节点中,相邻节点的中点满足条件: 中点处无对应节点 或 对应节点已被访问过
用图来做实在是复杂。。光是求出所有有效路径这个问题都让我头大。。。
于是有了这个排列组合方法:
我们可以这样解决这个问题:
1.遍历 i in range(m,n+1)
2.遍历从9个节点中抽出i个节点的所有组合
3.遍历i个节点的所有排列,排列顺序即i个节点的访问顺序
4.判断是否满足中点条件

代码如下:

#define calMiddle(x,y) (x+y)/2struct myPoint
{int x, y;
};class Solution {public:int solution(int m, int n) {for (int i = m; i < n + 1; i++){if (i == 0) {result += 0;continue;}if (i == 1) {result += 9;continue;}if (i == 2) {result += 56;continue;}if (i > 9)continue;//遍历所有组合并判断combine(pointList, i);}//for (size_t i = m; i <= n; i++)//{//  if (i > 9) {//      continue;//  }//  result += results[i];//}return result;}private:void combine(const vector<myPoint>& targets, int k) {if (k < 0) {cout << "k < 0  in  combine()" << endl;exit(-1);}if (k == 0)return;vector<int> indexes;for (int i = 0; i < k; i++){indexes.push_back(i);}combineRecursion(targets, indexes);return;}//组合的递归函数,实现了给定组合数的数组的遍历。//通用于如下情景:需要从一个数组percents中抽取indexes.size()个数,对于每一种组合都要进行某一操作。//percents:抽取组合对象列表//indexes:抽取到的下标列表void combineRecursion(const vector<myPoint>& targets, vector<int>& indexes) {int targetsSize = targets.size(), indexesSize = indexes.size();//最后一位是否到达终点bool lastIsEnd = (indexes.back() == targetsSize - 1);//如果最后一位未到达终点,则进行操作,更新参数,继续递归if (!lastIsEnd) {//--------------operation-----------------//combineOperation(targets, indexes);//--------------operation-----------------////更新参数indexes.back()++;//继续递归combineRecursion(targets, indexes);//子函数结束后,当前函数也返回return;}//如果最后一位到达终点,则反向遍历,查询每一位是否到达终点bool currentIsEnd;for (size_t i = indexesSize - 2; i >= 0; i--){currentIsEnd = (indexes[i] == targetsSize - indexesSize + i);//如果上一位到达终点而当前位未到达终点,则进行操作,更新参数,继续递归if (lastIsEnd && !currentIsEnd) {//--------------operation-----------------//combineOperation(targets, indexes);//--------------operation-----------------////更新参数indexes[i]++;for (size_t j = i + 1; j < indexesSize; j++){indexes[j] = indexes[j - 1] + 1;}//继续递归combineRecursion(targets, indexes);//子函数结束后,当前函数也返回return;}//如果第0位也到达终点,则进行操作,结束递归if (i == 0 && currentIsEnd) {//--------------operation-----------------//combineOperation(targets, indexes);//--------------operation-----------------//return;}}}void combineOperation(const vector<myPoint>& targets, vector<int>& indexes) {//遍历所有排列,进行操作permute(targets, indexes);}//给出一个数组,递归遍历该数组的所有排列void permute(const vector<myPoint>& targets, vector<int> indexes) {vector<int> indexes2 = indexes;permuOperation(indexes);while (prev_permutation(indexes.begin(), indexes.end())) {permuOperation(indexes);}while (next_permutation(indexes2.begin(), indexes2.end())) {permuOperation(indexes2);}}//permute函数的操作函数void permuOperation(const vector<int>& indexes) {myPoint middle, point0, point1, prePoint;bool flag0 = true, flag1 = false;//flag0--result,flag1--middle是否已按过的判断//遍历所有中点for (size_t i = 0; i < indexes.size() - 1; i++){point0 = pointList[indexes[i]];point1 = pointList[indexes[i + 1]];flag0 = true;//如果中点为整数if ((point0.x + point1.x) % 2 == 0 && (point0.y + point1.y) % 2 == 0) {//求中点middle.x = calMiddle(point0.x, point1.x);middle.y = calMiddle(point0.y, point1.y);//遍历判断中点是否按过for (size_t j = 0; j < i; j++){prePoint = pointList[indexes[j]];flag1 = false;//如果按过if (middle.x == prePoint.x&&middle.y == prePoint.y){flag1 = true;break;}}//中点如果未按过,则当前情况不满足要求if (!flag1) {flag0 = false;break;}}}if (flag0)result++;}const vector<myPoint> pointList = { {0,0},{0,1},{0,2},{1,0},{1,1},{1,2},{2,0},{2,1},{2,2} };const int pointListSize = pointList.size();int result = 0;int results[10] = { 0,9,56,320,1624,7152,26016,72912,140704,140704 };

【c++】牛客网 vivo2020届春季校园招聘在线编程考试题 手机锁屏的有效模式相关推荐

  1. 牛客网 vivo2020届春季校园招聘在线编程考试 第3题

    牛客网 vivo2020届春季校园招聘在线编程考试 第3题 1.问题分析 2.问题解决 3.总结 1.问题分析   主要就是两个数学公式.代码我已经进行了详细的注释,理解应该没有问题,读者可以作为参考 ...

  2. 牛客网vivo2020届春季校园招聘在线编程考试

    来源:牛客网vivo2020届春季校园招聘在线编程考试 https://www.nowcoder.com/question/next?pid=22390442&qid=925105&t ...

  3. 牛客网 vivo2020届春季校园招聘在线编程考试 第2题

    牛客网 vivo2020届春季校园招聘在线编程考试 第2题 1.问题分析 2.问题解决 3.总结 1.问题分析 基本思路是: 1.如果有因子大于等于 10 ,说明不存在 m,使得 m 的各位(个位.十 ...

  4. vivo2020届春季校园招聘在线编程考试 解题报告 Apare_xzc

    vivo2020届春季校园招聘在线编程考试 解题报告 题目链接:牛客链接 A. 手机屏幕解锁模式 分析: 这是一个智能手机的图案锁,有3*3=9个点.现在要求所有图案中经过的点的个数再[m,n]这个范 ...

  5. vivo2020届春季校园招聘在线编程考试--[编程题]vivo智能手机产能

    vivo2020届春季校园招聘在线编程考试--[编程题]vivo智能手机产能 题目 解题思路 代码块 题目 在vivo产线上,每位职工随着对手机加工流程认识的熟悉和经验的增加,日产量也会不断攀升. 假 ...

  6. vivo2020届春季校园招聘在线编程考试--[编程题]数位之积

    vivo2020届春季校园招聘在线编程考试--[编程题]数位之积 题目 解题思路 代码块 题目 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 256M,其他语言512M 现给定任意正 ...

  7. vivo2020届春季校园招聘在线编程考试 [编程题]vivo智能手机产能 C++实现

    [编程题]vivo智能手机产能 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 256M,其他语言512M 在vivo产线上,每位职工随着对手机加工流程认识的熟悉和经验的增加,日产量也 ...

  8. vivo2020届春季校园招聘在线编程考试 [编程题]数位之积 C++实现

    [编程题]数位之积 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 256M,其他语言512M 现给定任意正整数 n,请寻找并输出最小的正整数 m(m>9),使得 m 的各位(个 ...

  9. vivo2020届春季校园招聘在线编程考试

    1/3 [编程题]手机屏幕解锁模式 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 256M,其他语言512M 现有一个 3x3 规格的 Android 智能手机锁屏程序和两个正整数  ...

最新文章

  1. MVC小型商务网站实例(2)--项目架构
  2. 37个JavaScript基本面试问题和解答
  3. [转]第(前)k大数问题
  4. Python手册 3.7
  5. java之跳转_java学习之五种跳转关于jsp的
  6. 复旦大学在职MBA项目2011年度学费调整通知
  7. UVa 1583 Digit Generator(枚举+打表)
  8. java中流关闭如何打开_关于java中流关闭的问题
  9. 数据结构/图论:最小路径问题
  10. 烂泥:apache虚拟主机的学习与应用
  11. Python Scrapy 创建第一个爬虫项目
  12. ubuntu下CHM阅读器
  13. 7.计算机网络的发展 计算机网络发展背景 原因 阿帕网与计算机网络 通信方式 电路 报文 分组 包 交换 卡恩 瑟夫 网络控制协议 NCP TCP ip诞生发展 tcp 协议族 应用编程接口
  14. 正向代理与反向代理的区别,为什么要有正向代理和反向代理
  15. IPv6进阶:IPv6 过渡技术之 6to4 自动隧道
  16. linux 下载jdk方式
  17. 快速上手!java淘宝客(springboot)
  18. 腾讯内容处理和分发中的算法应用探究
  19. 项目经验:抽奖程序(Python)
  20. 2016 Google hosts 持续更新【更新于:2016-04-10】

热门文章

  1. 【高质量github项目合辑】视频、文本的特征提取
  2. 小团队?大团队?优缺点对比
  3. 有符号数和无符号数负数
  4. 基于51单片机DS1302的LCD电子时钟
  5. python-opencv 识别图片中的人脸
  6. Navicat 12 for MySQL最新版激活(注册机)
  7. 图像几何失真与局部增强
  8. 学习笔记 -- 用python中的selenium模拟知乎登录
  9. ajax返回的数据有问题,ajax请求成功返回数据,转成数组后,for遍历取不到值的有关问题...
  10. 告软件测试初学者:入门需掌握的知识点