• 剑指offer自学系列(三)


    题目描述:

    输入一个整数数组,实现一个函数来调整该数组中数字的顺序,使得所有的奇数位于数组的前半部分,所有的偶数位于数组的后半部分,并保证奇数和奇数,偶数和偶数之间的相对位置不变,例如{5,1,4,2,7,0,6,9},结果为{5,1,7,9,4,2,0,6}

    题目分析:

    题目要求分开奇数和偶数,还需要保持奇数和偶数相对顺序不变,首先想到的是采用两个额外数组分别存奇数和偶数,然后将两个额外数组按奇数在前,偶数在后连接到一起,但是由于未知奇数和偶数的数量,我们申请的两个额外数组为保险起见都设为和原数组一样长,这就造成了空间上的浪费,可不可以更加优化一点,我们采用一个数组,从头往后检索原数组,如果是奇数,则置入新申请的数组,为了降低时间复杂度,我们同时设置一根指针从后往前同时检索,遇到偶数则倒着插入额外申请的数组,这样在o(n)的时间复杂度内可以实现该算法

    下面是代码:

    #include<iostream>
    using namespace std;
    
    void OddEven(int A[],int B[],int len) {
        int j = 0;
        for (int i = 0; i < len;++i) {
            if (A[i]%2 == 1) {
                B[j] = A[i];
                j = j + 1;
            }
        }
        int k = len - 1;
        for (int i = len - 1; i >= 0; --i) {
            if (A[i]%2==0) {
                B[k] = A[i];
                k = k - 1;
            }
        }
        for (int i = 0; i < len; ++i) {
            cout << B[i]<<endl;
        }
    }
    
    int main() {
        int A[8] = {5,1,4,2,7,0,6,9};
        int B[8];
        int len = 8;
        OddEven(A, B, len);
        return 0;
    }

    题目描述:输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字,例如,如果输入如下4x4矩阵,

    1    2    3    4

    5    6    7    8

    9   10  11  12

    13 14  15  16

    顺时针输出结果:1,2,3,4,8,12,16,15,14,13,9,5,6,7,11,10

    题目分析:对矩阵来说,我们需要对各种情况分析,从下面图可以看出,最外层按圈的方式遍历,最里面会出现很多种情况

    image_thumb[22]image_thumb[19]image_thumb[20]image_thumb[21]

    我们采用顺序遍历的方式,首先从左往右,然后从上往下,从右回到左,从下回到上,一轮下来,外环走完,第二轮从内环遍历,左和上初始条件加一,右和下初始条件减一,结束条件是左边界超过右边界以及上边界超过下边界,下面是代码:

    #include<iostream>
    #include<vector>
    using namespace std;
    
    vector<int> CircleValue(vector<vector<int>> matrix) {
        int row = matrix.size();
        int col = matrix[0].size();
        int left = 0;
        int right = col - 1;
        int top = 0;
        int bottom = row - 1;
        vector<int> result;
        while (left<=right&&top<=bottom) {
            for (int i = left; i <= right;i++) {
                result.push_back(matrix[top][i]);
            }
            for (int j = top+1; j <= bottom; ++j) {
                result.push_back(matrix[j][right]);
            }
            if (top!=bottom) {
                for (int i = right - 1; i >= left;--i) {
                    result.push_back(matrix[bottom][i]);
                }
            }
            if (left!=right) {
                for (int j = bottom - 1; j > top;--j) {
                    result.push_back(matrix[j][left]);
                }
            }
            left++; top++; right--; bottom--;
        }
        return result;
    }
    
    int main() {
        vector<vector<int>> arr;
        int row;
        int col;
        cin >> row >> col;
        arr.resize(row);
        
        for (int i = 0; i < row; i++){
                arr[i].resize(col);
            }
        
        cout << "请输入数组元素:" << endl;
        
        for (int m = 0; m < row; m++){
                for (int n = 0; n < col; n++){
                         cin >> arr[m][n];
                }
        }
        vector<int> B;
        B = CircleValue(arr);
        vector<int>::iterator t;
        for (t = B.begin(); t != B.end(); t++)
            cout << *t << " ";
    }

    C++向量补充知识:

    向量是重要的数据结构,和数组有很多相似的地方

    向量声明#include<vector>

    首先是一维向量性质:

    vector<int> arr = {1,2,3,4,5,6,7,8};

    arr.size()返回向量长度

    arr.empty()判断向量是否为空

    arr.begin()向量的第一个元素

    arr.end()向量的最后一个元素

    arr.insert(arr.begin(),1000)将1000插到向量初始值前面

    arr.clear()清空向量

    arr.ease(arr.begin(),arr.end())删除开始到结尾这个区间的值

    arr.push_back()往向量中压入一个值

    arr.pop()默认弹出最后一个值

    一维向量输出的两种方法:

    vector<int>::iterator t;
    for (t = arr.begin(); t != arr.end(); t++)
        cout << *t << " ";
    for (int i = 0; i < arr.size(); i++)
        cout << B[i] << " ";

    对于二维向量:

    二维向量扩容(row,col)

    arr.resize(row);
    for (int i = 0; i < row; i++)
    {        
        arr[i].resize(col);
    }

    二维数组赋初值

    vector<vector<int>> arr = { {1,2,3,4},{5,6,7,8},{9,10,11,12},{13,14,15,16}};

    二维数组输出

    for (int i = 0; i < arr.size(); i++)
          for(int j=0;j<arr[0].size();j++)
              cout << arr[i][j] << " ";

    参考:

    https://www.cnblogs.com/wanglei5205/p/8617424.html(剑指offer方法)

    https://blog.csdn.net/qq_36427732/article/details/79652430(向量使用方法)

  • 相关阅读:
    【转载】Android IntentService使用全面介绍及源码解析
    【转载】作为Android开发者,你真的熟悉Activity吗?
    【转载】从使用到原理学习Java线程池
    Linux 基础知识+常见命令
    Python中的字典合并
    Python的__hash__函数和__eq__函数
    C#中实现Hash应用
    深入理解python元类
    Docker搭建Gitlab服务器
    python的加密方式
  • 原文地址:https://www.cnblogs.com/51selfstudy/p/10659195.html
Copyright © 2020-2023  润新知