赞
踩
题目描述:
Leetcode
解题思路:
二分法
如上图所示 ,因为该矩阵行列都是从小到大排列的,我们可以知道该矩阵的最大值15和最小值1,因此对于任意一个mid(min<mid<max)都可以知道矩阵中大于小于该元素值的个数。例如,mid=8,我们可以知道矩阵中小于8的个数为2。用类似的思想就可以解出该题。
以上图矩阵为例,求第k=8小对应的元素,实现过程如下:
step 1:left=1,right=15,mid=8 count=2<k=8说明此时的范围太小,应该扩大范围
step 2:left=mid+1=9,right=15,mid=12 count=6<k=8
step3:left=mid+1=13,right=15,mid=14,count=8=k=8说明此时第k小在该范围内,即矩阵中小于等于13的数是8个但是我们还不能确定矩阵中第8小是谁
step4:left=13,right=mid=14,mid=13,count=8=k=8
step5:left=13,right=13,收敛
如何计算矩阵内小于等于mid的个数参考:
思想类似于
240.搜索二维矩阵
如图,从左到右,从上到下计算小于等于mid的数目
#include<iostream> #include<vector> using namespace std; class Solution { public: int CalculateCount(vector<vector<int>>&matrix,int target){ int count = 0; int row = matrix.size(), col = matrix[0].size(); int i = 0, j = col - 1; while(i<row&&j>=0) { if(target>=matrix[i][j]) { count = count + j+1; i++; } else{ j--; } } return count; } int kthSmallest(vector<vector<int>>& matrix, int k) { int m,n; m = n = matrix.size(); int low = matrix[0][0], high = matrix[m - 1][n - 1], mid = 0; int count = 0; if(n==1) return matrix[0][k - 1]; while(low!=high){ mid = (low + high) / 2; cout << mid << " "; count = CalculateCount(matrix, mid); cout << count<<endl; if(count<k) low = mid + 1;//矩阵中大于Mid的数有count,count<k说明Mid的范围太小了,应该扩大 else high = mid;//count>=k说明第k小的数包好在[low,mid]的范围(范围过大),但是具体在哪还不确定需要进一步细化 } return low; } }; int main() { int m = 3, n = 3; int target = 5; vector<vector<int>> matrix(m, vector<int>(n)); vector<int> v; int i, j; for (i = 0; i < m;i++) for (j = 0; j < n;j++) cin >> matrix[i][j]; Solution sl; int value = sl.kthSmallest(matrix, 8); cout << value<<endl; /* for (i = 0; i < m;i++) { for (j = 0; j < n;j++) cout << matrix[i][j] << " "; cout << endl; }*/ return 0; }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。