二维有序数组查找

点:逻辑思维。抽象问题并将问题分为子问题 


题意:一个二维数组,每一行按行都是有序的,每一列按列也是有序的,如下图的二维数组,每一行每一列,都是升序排列

如数组:

1 2 8 9 10

2 4 9 12 17

4 7 10 13 21

5 8 11 15 23

7 13 15 18 25

这时需要找到某一数字,如何能够找到、高效的找到。

剑指offer面试题3


思路:比如数组是升序,那么行从第一行起,列顺序从后向前找,

1、当找到这个数就输出并且退出这行的查找,因为这行其他的数,不会再找到要找的数了

2、如果找到比这个数小的数,比如找的是7,在第一行找到2比7小,那么就确定了这个数的最小出现范围是“行0-4、列0-1”,上一个比7大的8,无论从行还是列都只会比8更大,肯定找不到7。确定了范围就可以简单遍历查找了。


代码:

#include <iostream>

int main (int argc, char *argv[]) {
    if (argc < 2) {
        std::cout << "input find num" << std::endl;
        return 0;
    }
    int data[5][5] = {{1, 2, 8, 9, 10}, {2, 4, 9, 12, 17}, {4, 7, 10, 13, 21}, {5, 8, 11, 15, 23}, {7, 13, 15, 18, 25}};

    int row = 5, column = 5;
    for (int i = 0; i < row; i++) {
        for (int j = 0; j < column; j++) {
            std::cout << data[i][j] << "\t";
        }
        std::cout << std::endl;
    }
    
    int find = std::stoi(argv[1]);
    bool flag = false;
    for (int i = 0; i < row; i++) {
        for (int j = column - 1; j >= 0; j--) {
            if (find == data[i][j]) {
                std::cout << "direct find " << i << "," << j << std::endl;
                flag = true;
                break;
            } else if (find > data[i][j]) {
                std::cout << "find range row: " << i << "-" << row - 1 << ", column: " << 0 << "-" << j << std::endl;
                int r = i, c = j;
                for (int ii = r; ii < row; ii++) {
                    for (int jj = j; jj >= 0; jj--) {
                        if (data[ii][jj] == find) {
                            std::cout << "find " << ii << "," << jj << std::endl;
                            flag = true;
                        }
                    }
                }
                if (flag) {
                    break;
                }
            }
            if (flag) {
                break;
            }
        }
    }
    if (!flag) {
        std::cout << "not find" << std::endl;
    }
    
    return 0;
}




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值