您的位置:首页 > 其它

Leetcode Search a 2D Matrix 搜索二维表

2014-01-02 08:48 302 查看


Search a 2D Matrix

Write an efficient algorithm that searches for a value in an m x n matrix. This matrix has the following properties:

Integers in each row are sorted from left to right.
The first integer of each row is greater than the last integer of the previous row.

For example,

Consider the following matrix:
[
  [1,   3,  5,  7],
  [10, 11, 16, 20],
  [23, 30, 34, 50]
]


Given target =
3
, return
true
.
这道题的解法倒是很多的,网上也有不少分析的。

比如LeetCode论坛上有分析非常仔细的,不过他好像推荐的是个O(n+m)的时间效率,这次也是个例外了,他的分析和例子都不好。

因为这道题的最优时间效率应该是O(lgm +lgn); m,n 代表行和列数,而且也没有那么复杂,不过就是考二分法的运用,能够灵活运用了做这道题不是难事,本人一次性通过。

这里是使用二分法,先列二分,然后行二分,看似复杂,其实是很简单的程序。不用看Leetcode上的那么长编大论的分析。

下面是我的程序,看起来长,其实结构很清晰,很好理解的程序。

const static int FOUND = -2;
	const static int NOT_FOUND = -1;

	bool searchMatrix(vector<vector<int> > &matrix, int target) 
	{
		int found_mark = searchRow(matrix, 0, matrix.size()-1, target);
		if (found_mark == NOT_FOUND) return false;
		if (found_mark == FOUND) return true;

		found_mark = searchCol(matrix, found_mark, 0, matrix[0].size()-1, target);

		if (found_mark == NOT_FOUND) return false;
		return true;
	}

	int searchRow(vector<vector<int> > &m, int low, int up, int tar)
	{
		//up = -1的时候也是等于NOT_FOUND,所以设NOT_FOUND=-1
		if (low > up) return up;

		int mid = low + ((up - low)>>1);
		if (tar < m[mid][0])
		{
			return searchRow(m, low, mid-1, tar);
		}
		else if (m[mid][0] < tar)
		{
			return searchRow(m, mid+1, up, tar);
		}
		else return FOUND;
	}

	int searchCol(vector<vector<int> > &m, int row, int left, int right, int tar)
	{
		if (left > right) return NOT_FOUND;

		int mid = left + ((right - left)>>1);
		if (tar < m[row][mid])
		{
			return searchCol(m, row, left, mid-1, tar);
		}
		else if(m[row][mid] < tar)
		{
			return searchCol(m, row, mid+1, right, tar);
		}
		else return FOUND;
	}


下面也看看Leetcode上的程序,也是很简单的,不过他说这个也许是面试官需要的答案?那我就怀疑了,O(lgn + lgm)比O(n+m)提高了一个档次的时间复杂度啊,当然是二分法好啦。

//属于上下行,左右列夹并追踪目标的方法,复杂度O(n+m)
	bool searchMatrix2(vector<vector<int> > &matrix, int target) {
		int m(matrix.size()-1), n(matrix[0].size()), k(0);
		while(m>=0 && k<n){
			if(matrix[m][k]==target) return true;
			else if(matrix[m][k]>target) --m;
			else ++k;
		}
		return false;
	}


//2004-2-11 update
	bool searchMatrix(vector<vector<int> > &matrix, int target) 
	{
		int row = colSearch(matrix, 0, matrix.size()-1, target);
		if (row == -1) return false;
		return rowSearch(matrix, row, 0, matrix[row].size()-1, target);
	}
	int colSearch(vector<vector<int> > &m, int c1, int c2, int tar)
	{
		if (c1 > c2) return -1;
		int mid = c1 + ((c2-c1)>>1);
		if (m[mid][0]<=tar && tar<=m[mid].back()) return mid;
		if (m[mid][0] < tar) return colSearch(m, mid+1, c2, tar);
		if (tar < m[mid][0]) return colSearch(m, c1, mid-1, tar);
		return -1;
	}
	bool rowSearch(vector<vector<int> > &m, int row, int r1, int r2, int tar)
	{
		if (r1 > r2) return false;
		int mid = r1 + ((r2-r1)>>1);
		if (m[row][mid] < tar) return rowSearch(m, row, mid+1, r2, tar);
		if (tar < m[row][mid]) return rowSearch(m, row, r1, mid-1, tar);
		return true;
	}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: