ch8 - Data Structure 數據結構

線性數據結構 - Queue、Stack、Hash
樹型數據結構 - Heap / Priority Queue、TreeMap

BFS的主要數據結構是 Queue
DFS的主要數據結構是 Stack

目錄:

    1. 什麼是數據結構
      1.1 分類
      1.2 什麼是數據結構?
    1. 隊列 Queue
      2.1 基礎知識
      2.2 相關題目 - BFS相關的題目
    1. 棧 Stack
      3.1 基礎知識
      3.2 相關題目 - 非遞歸實現DFS的主要數據結構
      3.3 min-stack 帶最小值操作的棧(12 in lintcode)
      3.4 largest-rectangle-in-histogram 直方圖最大矩陣覆蓋(122 in lintcode)
      3.5 maximal-rectangle 最大矩陣(510 in lintcode)
    1. 哈希表 Hash - 見相關筆記
    1. 樹型數據結構 - 見相關筆記,包括Heap / Priority Queue、TreeMap

1. 什麼是數據結構 -

1.1 分類

1.2 什麼是數據結構?

1). 數據結構 = 集合 + 集合上的若干操作
2). 可以在鏈表上進行二分法嗎?

不可以,因爲二分法複雜度爲O(n),(O(n) = O(n/2) + O(1)) O(1)鏈表不能達到

3). 定義一種數據結構,必須要定義該數據結構支持的操作,以及操作的時間複雜度是什麼
4). 所有的數據結構落實到底層數據結構均爲2種:
  • 數組(連續空間)
  • 鏈表(離散空間)

2. 隊列 Queue -

2.1 基礎知識

1). 先進先出。
2). 支持的操作: O(1) Push / O(1) Pop / O(1) Top
3). BFS的主要數據結構。多做BFS的題目就可以了。
4). 實現隊列的話,數組和鏈表均可,linkedList更常用,c++中的vector、java中的ArrayList,是動態數組,每次空間不夠時乘2。還可以使用循環數組實現隊列。
5). 建議用數組和鏈表把隊列都實現一遍。

2.2 相關題目 - BFS相關的題目

3. 棧 Stack - 非遞歸實現DFS的主要數據結構

3.1 基礎知識

1). 後進先出,在末尾操作
2). 支持的操作: O(1) Push / O(1) Pop / O(1) Top
3). DFS非遞歸實現的主要數據結構。多做BFS的題目就可以了。
4). 建議用數組和鏈表把隊列都實現一遍。

3.2 相關題目 - 非遞歸實現DFS的主要數據結構

3.3 min-stack 帶最小值操作的棧(12 in lintcode)

1.題目

http://www.lintcode.com/zh-cn/problem/min-stack/
http://www.jiuzhang.com/solution/min-stack/

實現一個帶有取最小值min方法的棧,min方法將返回當前棧中的最小值。
你實現的棧將支持push,pop 和 min 操作,所有操作要求都在O(1)時間內完成。

樣例
如下操作:push(1),pop(),push(2),push(3),min(), push(1),min() 返回 1,2,1

2.代碼

1). 典型的數據結構的實現題
2). 分析:

2個stack,保存最小值得變化序列。每次push、pop時,需要更新存最小值的棧。

3). 代碼

在這裏插入圖片描述

3.4 largest-rectangle-in-histogram 直方圖最大矩陣覆蓋(122 in lintcode)

1.題目

http://www.lintcode.com/zh-cn/problem/largest-rectangle-in-histogram/
http://www.jiuzhang.com/solution/largest-rectangle-in-histogram/

Given n non-negative integers representing the histogram’s bar height where the width of each bar is 1, find the area of largest rectangle in the histogram.
Above is a histogram where width of each bar is 1, given height = [2,1,5,6,2,3].
The largest rectangle is shown in the shaded area, which has area = 10 unit.

樣例
給出 height = [2,1,5,6,2,3],返回 10
在這裏插入圖片描述

2.思路 &代碼

1). 分析:

最多有n2種組合,理論上複雜度可以降到n2。

如果複雜度爲多項式(n^2 ,n3,n4… ),則一定不用dp,dp適合複雜度爲2^n的。

2). 求解

解法1:-時間複雜度O(n^2),會超時 TLE

A.兩個for循環,startIndex,endIndex。
挪動endIndex時,記錄最小值,並將計算到的面積與全局面積比較。

B. 出現TLE的可能情況
- 複雜度太高;
- 死循環 (如二分法或者鏈表等複雜度不高的元素出現超時,一定是死循環了)

解法2:- O(n)

A. nlogn的可能算法有以下三種:
- Divide & Conqure, O(n) 分爲2部分,遞歸,如merge sort
- 先排序,再用O(n)搞定
- for一遍,內部支持logn的數據結構,如heap/priority queue / TreeMap 求最大最小值

B. 本題使用 單調棧,複雜度是O(n)
- 單調棧可以找到某個數左邊(右邊)第一個比他小的數
在這裏插入圖片描述

3.5 maximal-rectangle 最大矩陣(510 in lintcode)

1.題目

http://www.lintcode.com/zh-cn/problem/maximal-rectangle/
http://www.jiuzhang.com/solution/maximal-rectangle/

給你一個二維矩陣,權值爲False和True,找到一個最大的矩形,使得裏面的值全部爲True,輸出它的面積

樣例
給你一個矩陣如下

[
  [1, 1, 0, 0, 1],
  [0, 1, 0, 0, 1],
  [0, 0, 1, 1, 1],
  [0, 0, 1, 1, 1],
  [0, 0, 0, 0, 1]
]

輸出6

2.思路 & 代碼

此題是之前那道的 Largest Rectangle in Histogram 直方圖中最大的矩形 的擴展,這道題的二維矩陣每一層向上都可以看做一個直方圖,輸入矩陣有多少行,就可以形成多少個直方圖,對每個直方圖都調用 Largest Rectangle in Histogram 直方圖中最大的矩形 中的方法,就可以得到最大的矩形面積。那麼這道題唯一要做的就是將每一層構成直方圖,由於題目限定了輸入矩陣的字符只有 ‘0’ 和 ‘1’ 兩種,所以處理起來也相對簡單。方法是,對於每一個點,如果是‘0’,則賦0,如果是 ‘1’,就賦 之前的height值加上1。具體參見代碼如下:

class Solution {
public:
    int maximalRectangle(vector<vector<char>>& matrix) {
        if (matrix.empty() || matrix[0].empty()) return 0;
        int res = 0, m = matrix.size(), n = matrix[0].size();
        vector<int> height(n + 1, 0);
        for (int i = 0; i < m; ++i) {
            stack<int> s;
            for (int j = 0; j < n + 1; ++j) {
                if (j < n) {
                    height[j] = matrix[i][j] == '1' ? height[j] + 1 : 0;
                }
                while (!s.empty() && height[s.top()] >= height[j]) {
                    int cur = s.top(); s.pop();
                    res = max(res, height[cur] * (s.empty() ? j : (j - s.top() - 1)));
                }
                s.push(j);
            }
        }
        return res;
    }
};
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章