st表,单数组不清空,60pts

P1886 滑动窗口 /【模板】单调队列

hzx198 @ 2024-08-16 23:19:05

如题,以下60分:

#include <bits/stdc++.h>
using namespace std;
typedef long long ll;

const ll N = 1e6 + 5;

ll n, k, st[N][17], a[N];

// log2预处理
ll lg[N];
void init_log2(ll n) {
  lg[1] = 0;
  for (ll i = 2; i <= n; i++) lg[i] = lg[i >> 1] + 1;
}

void buildmax(ll n) {
  // j为区间长度, j <= log2(n)
  for (ll j = 1; (1 << j) <= n; j++) {
    // i为左端点, i <= n - 2^j + 1
    for (ll i = 1; i <= n - (1 << j) + 1; i++) {
      st[i][j] = max(st[i][j - 1], st[i + (1 << (j - 1))][j - 1]);
    }
  }
}

void buildmin(ll n) {
  // j为区间长度, j <= log2(n)
  for (ll j = 1; (1 << j) <= n; j++) {
    // i为左端点, i <= n - 2^j + 1
    for (ll i = 1; i <= n - (1 << j) + 1; i++) {
      st[i][j] = min(st[i][j - 1], st[i + (1 << (j - 1))][j - 1]);
    }
  }
}

ll getmax(ll l, ll r) {
  ll len = lg[r - l + 1];
  return max(st[l][len], st[r - (1 << len) + 1][len]);
}

ll getmin(ll l, ll r) {
  ll len = lg[r - l + 1];
  return min(st[l][len], st[r - (1 << len) + 1][len]);
}

int main(void) {
  ios::sync_with_stdio(false);
  cin.tie(nullptr), cout.tie(nullptr);
  cin >> n >> k;
  for (ll i = 1; i <= n; i++) cin >> a[i], st[i][0] = a[i];
  init_log2(n);

  buildmin(n);
  for (ll i = 1; i <= n - k + 1; i++) cout << getmin(i, i + k - 1) << ' ';
  cout << '\n';

  // memset(st, 0, sizeof(st));
  // for (ll i = 1; i <= n; i++) st[i][0] = a[i];
  buildmax(n);
  for (ll i = 1; i <= n - k + 1; i++) cout << getmax(i, i + k - 1) << ' ';
  return 0;
}

把注释去掉就ac了:

#include <bits/stdc++.h>
using namespace std;
typedef long long ll;

const ll N = 1e6 + 5;

ll n, k, st[N][17], a[N];

// log2预处理
ll lg[N];
void init_log2(ll n) {
  lg[1] = 0;
  for (ll i = 2; i <= n; i++) lg[i] = lg[i >> 1] + 1;
}

void buildmax(ll n) {
  // j为区间长度, j <= log2(n)
  for (ll j = 1; (1 << j) <= n; j++) {
    // i为左端点, i <= n - 2^j + 1
    for (ll i = 1; i <= n - (1 << j) + 1; i++) {
      st[i][j] = max(st[i][j - 1], st[i + (1 << (j - 1))][j - 1]);
    }
  }
}

void buildmin(ll n) {
  // j为区间长度, j <= log2(n)
  for (ll j = 1; (1 << j) <= n; j++) {
    // i为左端点, i <= n - 2^j + 1
    for (ll i = 1; i <= n - (1 << j) + 1; i++) {
      st[i][j] = min(st[i][j - 1], st[i + (1 << (j - 1))][j - 1]);
    }
  }
}

ll getmax(ll l, ll r) {
  ll len = lg[r - l + 1];
  return max(st[l][len], st[r - (1 << len) + 1][len]);
}

ll getmin(ll l, ll r) {
  ll len = lg[r - l + 1];
  return min(st[l][len], st[r - (1 << len) + 1][len]);
}

int main(void) {
  ios::sync_with_stdio(false);
  cin.tie(nullptr), cout.tie(nullptr);
  cin >> n >> k;
  for (ll i = 1; i <= n; i++) cin >> a[i], st[i][0] = a[i];
  init_log2(n);

  buildmin(n);
  for (ll i = 1; i <= n - k + 1; i++) cout << getmin(i, i + k - 1) << ' ';
  cout << '\n';

  memset(st, 0, sizeof(st));
  for (ll i = 1; i <= n; i++) st[i][0] = a[i];
  buildmax(n);
  for (ll i = 1; i <= n - k + 1; i++) cout << getmax(i, i + k - 1) << ' ';
  return 0;
}

但这两次完全相同的st表预处理不应该覆盖掉数据吗,求解


|