leetcode 444. Sequence Reconstruction
leetcode 444. Sequence Reconstruction
Check whether the original sequence org
can be uniquely reconstructed from the sequences in seqs
. The org sequence is a permutation of the integers from 1 to n, with 1 ≤ n ≤ 104. Reconstruction means building a shortest common supersequence of the sequences in seqs
seqs
and it is the org
sequence.
Example 1:
Input: org: [1,2,3], seqs: [[1,2],[1,3]] Output: false Explanation: [1,2,3] is not the only one sequence that can be reconstructed, because [1,3,2] is also a valid sequence that can be reconstructed.
Example 2:
Input:
org: [1,2,3], seqs: [[1,2]]
Output:
false
Explanation:
The reconstructed sequence can only be [1,2].
Example 3:
Input: org: [1,2,3], seqs: [[1,2],[1,3],[2,3]] Output: true Explanation: The sequences [1,2], [1,3], and [2,3] can uniquely reconstruct the original sequence [1,2,3].
Example 4:
Input:
org: [4,1,5,2,6,3], seqs: [[5,2,6,3],[4,1,5,2]]
Output:
true
UPDATE (2017/1/8):
The seqs parameter had been changed to a list of list of strings (instead of a 2d array of strings). Please reload the code definition to get the latest changes.
思路:
這個題是讓我們遍歷所有 seqs
序列來推斷是否可以唯一確定所給出的org
,換句話說就是求拓撲排序 ;
這裡對 example
中的例子稍作解釋,例如example 1
與 example 3
:
這兩個例子中所給定的 org
是完全一樣的[1,2,3]
,但是seqs
序列中example 1
中給定的是[1,2],[2,3]
而example 3
中給定的是[1,2],[1,3],[2,3]
,這裡我們可以假設給定的 seqs
序列是可以邊疊加在同一個有向圖中的依賴序列,那麼可推出:
接著我們對這兩個圖示進行拓撲排序,我們每次都從出度最多的節點出發,在出發前檢查是否這個點是否是隻有出度,如果存在入度,那麼去找它的入度節點中出度數目最大的,那麼example 1
可推出序列:[1,2,3]或者[1,3,2];example 3
可以推出序列:[1,2,3];所以從這裡我們就可以從example 3
中唯一確定原序列,而example 1
並不可以。
程式碼:
class Solution {
public:
bool sequenceReconstruction(vector<int>& org, vector<vector<int>>& seqs) {
if (seqs.empty()) return false;
int n = org.size(), cnt = n - 1;
vector<int> pos(n + 1, 0), flags(n + 1, 0);
bool existed = false;
for (int i = 0; i < n; ++i) pos[org[i]] = i;
for (auto& seq : seqs) {
for (int i = 0; i < seq.size(); ++i) {
existed = true;
if (seq[i] <= 0 || seq[i] > n) return false;
if (i == 0) continue;
int pre = seq[i - 1], cur = seq[i];
if (pos[pre] >= pos[cur]) return false;
if (flags[cur] == 0 && pos[pre] + 1 == pos[cur]) {
flags[cur] = 1; --cnt;
}
}
}
return cnt == 0 && existed;
}
};