Ma trận n_rows x n_cols toàn 0. Hàm flip() chọn ngẫu nhiên một ô 0, đặt thành 1, trả về tọa độ. Hàm reset() đặt lại toàn 0. Tối ưu hóa số lần gọi random.
Thuật toán (Mapping + Fisher-Yates idea)
- Tổng ô
size = n*m. Mapholeslưu mapping cho các ô đã flip. flip(): randomidtrong[0, size-1], giảmsize. Nếuidtrongholeslấy giá trị thật. Cập nhậtholes[old_id] = holes[size] hoặc size. Trả về(id/m, id%m).reset(): khôi phụcsize, xóaholes.
Mã nguồn C++
#include <bits/stdc++.h>
using namespace std;
class Solution {
unordered_map holes;
int n, m, size;
public:
Solution(int n_rows, int n_cols) : n(n_rows), m(n_cols), size(n_rows*n_cols) {
srand(time(NULL));
}
vector flip() {
int id = rand() % size;
size--;
int rid = id;
if (holes.count(id)) id = holes[id];
holes[rid] = holes.count(size) ? holes[size] : size;
return {id / m, id % m};
}
void reset() {
size = n * m;
holes.clear();
}
};
Ví dụ
Ma trận 2x2, flip 4 lần → trả về 4 tọa độ khác nhau.