面试常考算法题总结(一)

原创 2016年08月29日 23:09:40

题目链接:面试常考算法题(一)

题目1:请把一张窄纸条竖着放在桌上,然后从纸条的下边向上对折,压出折痕后再展开。此时有1条折痕,突起的一面向指向纸条的背面,这条折痕叫做“下”折痕;突起的向指向纸条正面的折痕叫做“上”折痕。如果每次都从下边向上进行对折,对折N次。请从上到下计算出所有折痕的朝向。给定折的次数n,请返回从上到下的折痕的数组,若为下折痕则对应元素为"down",若为上折痕则为"up"。

测试样例:
1
返回:["down"]
分析:这题首先容易想到的是找规律,首先我们先对前几项结果进行观察:
n = 1, size = 1: "down",
n = 2, size = 3:  "down""down""up"
n = 3, size = 7:  "down""down""up""down""down""up""up"
可以观察到每次迭代的时候,数组的新size是前面size的2倍加上1,即size = 2*size+1,
前面的部分和上一组完全相同,最中间的值恒为"down",后半部分字节将前面的值翻转
并取反即可得到。talk is cheap,show me the code:
class FoldPaper {
public:
    vector<string> foldPaper(int n) {
        vector<string> res;
        if(n==1)
            res.push_back("down");
        else{
            vector<string> v = foldPaper(n-1);
            for(int i = 0;i<v.size();++i){
                res.push_back(v[i]);
            }
            res.push_back("down");
            reverse(v.begin(),v.end());
            for(int i = 0;i<v.size();++i){
                if(v[i]=="down")
                	res.push_back("up");
                else
                    res.push_back("down");
            }
        }
        return res;
    }
};

另一条思路是转化为二叉树的中序遍历,构建一颗二叉树,根节点是down,左子树的根是down,右子树的根节点是up。可以构造一个满二叉树,talk is cheap,show me the code:

class FoldPaper {
public:
    vector<string> foldPaper(int n) {
        // write code here
        vector<string> vec;
        pushs(vec,n,"down");
        return vec;
    }
    //中序遍历程序
    void pushs(vector<string> &vec,int n,string str)
    {
        if(n>0)
        {
            pushs(vec,n-1,"down");
            vec.push_back(str);
            pushs(vec,n-1,"up");
        }
    }
};
更多讨论见折纸问题

题目2:对于一个矩阵,请设计一个算法从左上角(mat[0][0])开始,顺时针打印矩阵元素。给定int矩阵mat,以及它的维数nxm,请返回一个数组,数组中的元素为矩阵元素的顺时针输出。
测试样例:
[[1,2],[3,4]],2,2
返回:[1,2,4,3]

分析:基本思路是不管简化矩阵,先顺时针打印矩阵外围的一圈,然后不断缩小矩阵即可,最后讨论一下只有一行或者一列的情形,talk is cheap,show me the code:

class Printer {
public:
    void clockwisePrint(const vector<vector<int>> &mat,vector<int> &res,int row1,int col1,int row2,int col2){
		//左上角(row1,col1)右下角(row2,col2)
        int i = row1,j=col1;
        while(j<=col2)   //上一行向右
            res.push_back(mat[i][j++]);
        --j,++i;
        while(i<=row2)   //右一行向下
            res.push_back(mat[i++][j]);
        --i,--j;
        if(row1 == row2 || col1 == col2) //只又一列或一行时,不向左,也不向上
            return;     
        while(j>=col1)  //下一行向左
            res.push_back(mat[i][j--]);
        ++j,--i;           
        while(i>row1)   //左一行向上,不打印左上角
            res.push_back(mat[i--][j]);           
    }
    vector<int> clockwisePrint(vector<vector<int> > mat, int n, int m) {
        int row1,row2,col1,col2;
        std::vector<int> res;
        for(row1 = 0,col1=0,row2=n-1,col2=m-1;row1<=row2 && col1<=col2;row1++,col1++,row2--,col2--)
            clockwisePrint(mat,res,row1,col1,row2,col2);
        return res;
    }
};

题目3:有一个NxN整数矩阵,请编写一个算法,将矩阵顺时针旋转90度。给定一个NxN的矩阵,和矩阵的阶数N,请返回旋转后的NxN矩阵,保证N小于等于300。

测试样例:
[[1,2,3],[4,5,6],[7,8,9]],3
返回:[[7,4,1],[8,5,2],[9,6,3]]

分析:找出旋转后的矩阵每个元素的位置在原来矩阵中对应位置之间的关系即可,talk is cheap,show me the code:

class Rotate {
public:
    vector<vector<int> > rotateMatrix(vector<vector<int> > mat, int n) {
        vector<vector<int> > vmat(n,vector<int>(n,0));
        for(int i = 0;i<n;++i){
            for(int j = 0;j<n;++j)
                vmat[i][j] = mat[n-1-j][i];
        }
        return vmat;
    }
};


题目4:对于一个矩阵,请设计一个算法,将元素按“之”字形打印。具体见样例。给定一个整数矩阵mat,以及他的维数nxm,请返回一个数组,其中元素依次为打印的数字。
测试样例:
[[1,2,3],[4,5,6],[7,8,9],[10,11,12]],4,3
返回:[1,2,3,6,5,4,7,8,9,12,11,10]

分析:行是奇数从左到右打印,行是偶数从右到左打印,talk is cheap,show me the code:

class Printer {
public:
    vector<int> printMatrix(vector<vector<int> > mat, int n, int m) {
        vector<int> res;
        int i = 0;
        while(i<n){
            if(i%2==0){
                for(int j = 0;j<m;++j)
                    res.push_back(mat[i][j]);
            }
            else{
                for(int j = m-1;j>=0;--j)
                    res.push_back(mat[i][j]);
            }
            ++i;
        }
        return res;
    }
};


题目5:对于一个字符串,和字符串中的某一位置,请设计一个算法,将包括i位置在内的左侧部分移动到右边,将右侧部分移动到左边。给定字符串A和它的长度n以及特定位置p,请返回旋转后的结果。
测试样例:
"ABCDEFGH",8,4
返回:"FGHABCDE"
分析:参考博客字符串移位的解题技巧。talk is cheap,show me the code:

class StringRotation {
public:
    string rotateString(string A, int n, int p) {
        return A.substr(p+1)+A.substr(0,p+1); 
    }
};


版权声明:本文为博主原创文章,未经博主允许不得转载。

互联网公司常见面试算法题

1、假设淘宝一天有5亿条成交数据,求出销量最高的100个商品并给出算法的时间复杂度。 先用哈希,统计每个商品的成交次数,然后再用在N个数中找出前K大个数的方法找出成交次数最多的前100个商品。 优...
  • jiangyanting2011
  • jiangyanting2011
  • 2017年04月21日 21:22
  • 3068

Java实现面试常考的算法

Java实现面试常考的算法 查找算法 排序算法 插入排序 选择排序 冒泡排序 快速排序Java实现面试常考的算法 我自己总结了几个平时面试问得一些算法题, 都是非常非常基础的问题. 查找算法 ...
  • u013144863
  • u013144863
  • 2016年11月20日 10:55
  • 8342

面试常考算法题总结(二)

题目链接:试卷1和试卷2。 题目1:对于一个无序数组A,请设计一个算法,求出需要排序的最短子数组的长度。给定一个整数数组A及它的大小n,请返回最短子数组的长度。 测试样例: [1,5,3,4,2...
  • JIEJINQUANIL
  • JIEJINQUANIL
  • 2016年08月30日 17:41
  • 1084

代码面试最常用的10大算法

在程序员的职业生涯中,算法亦算是一门基础课程,尤其是在面试的时候,很多公司都会让程序员编写一些算法实例,例如快速排序、二叉树查找等等。 本文总结了程序员在代码面试中最常遇到的10大算法类型,想要真正...
  • u012827205
  • u012827205
  • 2014年04月15日 14:45
  • 1909

代码面试最常用的10大算法

原文地址:http://bbs.csdn.net/topics/390768965
  • Mr__fang
  • Mr__fang
  • 2014年04月28日 13:51
  • 3597

经典算法面试题及答案

经典算法面试题及答案 2013-07-17 13:49:40 分类: C/C++ 1. 时针分针重合几次 表面上有60个小格,每小格代表一分钟, 时...
  • chenjie863
  • chenjie863
  • 2014年05月07日 16:48
  • 73143

算法经典面试题整理(java实现)

以下从Java角度解释面试常见的算法和数据结构:字符串,链表,树,图,排序,递归 vs. 迭代,动态规划,位操作,概率问题,排列组合,以及一些需要寻找规律的题目。 1. 字符串和数组 字符...
  • DUANJIEFEI
  • DUANJIEFEI
  • 2015年06月11日 19:23
  • 10068

数据结构与算法面试题80道

转自:http://hi.baidu.com/geogre_jsj/blog/item/e4b98fd2aab5aa3611df9b92.html 由于这些题,实在太火了。所以,应广...
  • jokes000
  • jokes000
  • 2011年12月14日 15:11
  • 123473

排序算法总结及面试题

排序算法的总结及其相关面试题
  • sunxianghuang
  • sunxianghuang
  • 2016年07月19日 11:48
  • 5043

面试常用算法总结——排序算法(java版)

面试常用算法总结——排序算法(java版)
  • XSF50717
  • XSF50717
  • 2015年08月06日 15:57
  • 9067
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:面试常考算法题总结(一)
举报原因:
原因补充:

(最多只允许输入30个字)