題目:二維數(shù)組中,每行從左到右遞增,每列從上到下遞增,設(shè)計(jì)一個(gè)算法,找其中的一個(gè)數(shù)
分析:
二維數(shù)組這里把它看作一個(gè)矩形結(jié)構(gòu),如圖所示:
1 | 2 | 8 | 9 |
2 | 4 | 9 | 12 |
4 | 7 | 10 | 13 |
6 | 8 | 11 | 15 |
在做這道題的時(shí)候我最先考慮的是每次比較對(duì)角線(xiàn)上的元素可能可以取得較好的效果,
以查找9為例,
從1(0,0)開(kāi)始,1<10,可以得出結(jié)論,10在1的右側(cè)或下側(cè);
1 | 2 | 8 | 9 |
2 | 4 | 9 | 12 |
4 | 7 | 10 | 13 |
6 | 8 | 11 | 15 |
然后看4(1,1),4<9,
1 | 2 | 8 | 9 |
2 | 4 | 9 | 12 |
4 | 7 | 10 | 13 |
6 | 8 | 11 | 15 |
然后看10(2,2),10>9,這個(gè)時(shí)候可以確定在10的右上方,或者左下方,
1 | 2 | 8 | 9 |
2 | 4 | 9 | 12 |
4 | 7 | 10 | 13 |
6 | 8 | 11 | 15 |
然后可以考慮使用遞歸黃色的兩個(gè)方框,設(shè)an>x時(shí)是(x,y),an-k>x時(shí)是(x0,y0),那么此次遞歸的起始點(diǎn)因該是:右上(x,y0),左下(x0,y)。
左下的方框,4(2,0),4<9;再看8(3,1),8<10,可以確定不在左下方框;
右上的方框,8(0,2),8<9;再看12(1,3),12>9,再次遞歸,(1,2)或(0,3)都可以找到。
看似可以解決問(wèn)題,但是,這個(gè)時(shí)候的矩形必須是正方形才行。。。。。。
如上圖所示,就沒(méi)辦法了(當(dāng)然,可以通過(guò)寬高的關(guān)系,計(jì)算出選擇縱向移動(dòng)多少次,橫向移動(dòng) 多少次,可以正好走個(gè)對(duì)角,但是,太麻煩了。。。。),所以,這么想是不對(duì)滴。。。。。。
然后我們考慮可以通過(guò)比較一次后可以去掉一行或者一列,那這個(gè)方法也可以算不錯(cuò)的了。
以查找10為例,
1.如果從左上角開(kāi)始找,1<10,發(fā)現(xiàn)除了一個(gè)個(gè)往后比沒(méi)有什么更好的辦法了 ;
2.如果從右上角(0,3)開(kāi)始找,9<10,由于每行從左到右遞增,所以可以把第一行(0)排除掉了;
1 | 2 | 8 | 9 |
2 | 4 | 9 | 12 |
4 | 7 | 10 | 13 |
6 | 8 | 11 | 15 |
然后看第二行最后一個(gè)數(shù)(1,3),12>10,由于每列從上到下遞增,所以可以把最后一列(3)排除;
1 | 2 | 8 | 9 |
2 | 4 | 9 | 12 |
4 | 7 | 10 | 13 |
6 | 8 | 11 | 15 |
然后看(1,2),9<10,排除行1;
1 | 2 | 8 | 9 |
2 | 4 | 9 | 12 |
4 | 7 | 10 | 13 |
6 | 8 | 11 | 15 |
然后看(2,2),10==10,找到目標(biāo),返回行列號(hào)。
3.除了從右上角開(kāi)始分析有較好的效果外,可以發(fā)現(xiàn)從左下角也可以以經(jīng)過(guò)一次比較排除一行或者是一列;從右下角分析則同1一樣,效率不高。
代碼:
package study;/** * 二維數(shù)組中,每行從左到右遞增,每列從上到下遞增, * 設(shè)計(jì)一個(gè)算法找其中的一個(gè)數(shù) * @author cnx * @CreateDate ; 2014年9月28日 上午10:14:21 */public class FindInMatrix { public static void main(String[] args) { FindInMatrix f = new FindInMatrix(); int a[] = f.find(f.a1, 12); if(a!=null) System.out.
新聞熱點(diǎn)
疑難解答
圖片精選
網(wǎng)友關(guān)注