#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef pair<int, int> ii;
const int INF = 1e9;
const ll LINF = 1e18;
const int N = 3e5 + 5;
const int MAX_A = 1e6 + 5;
// Ý tưởng: Đoán được max({D(a(i))}) sẽ không quá lớn (sau khi code để check thì ta biết được với a(i) <= 1e6 thì max({D(a(i))}) <= 240)
// Từ đó, ta có thể code brute-force để rút ra nhận xét:
// Với a(i) <= 1e6 thì mỗi a(i) tối đa chỉ bị tác động 6 lần
// Khi dùng Segment Tree thì độ phức tạp để update 1 vị trí là O(logn)
// => Mỗi vị trí tối đa bị tác động 6 lần => O(6 * logn)
// => Mảng có n phần tử: O(6 * nlogn)
// => Độ phức tạp: O(qlogn + 6 * nlogn) ~ O((q + n)logn)
struct Node {
int mx;
ll sum;
Node() {
mx = -INF, sum = 0;
}
Node(int x) {
mx = sum = x;
}
Node operator+(const Node& other) const {
Node c;
c.mx = max(mx, other.mx);
c.sum = sum + other.sum;
return c;
}
};
int n, q;
int a[N];
int D[MAX_A]; // D[i] = Số ước của i
void sieve() {
for (int i = 1; i < MAX_A; i++) {
for (int j = i; j < MAX_A; j += i) D[j]++;
}
}
// void brute() {
// int mx = 0;
// for (int i = 1; i < MAX_A; i++) {
// int tmp = i, cnt = 0;
// while (D[tmp] < tmp) tmp = D[tmp], cnt++;
// mx = max(mx, cnt);
// }
// cout << mx << '\n';
// }
Node seg[4 * N];
void build(int id, int l, int r) {
if (l == r) {
seg[id] = Node(a[l]);
return;
}
int mid = (l + r) >> 1;
build(id * 2, l, mid);
build(id * 2 + 1, mid + 1, r);
seg[id] = seg[id * 2] + seg[id * 2 + 1];
}
// Để check trong một đoạn có tồn tại vị trí nào cần được update nữa hay không thì
// ta quan tâm giá trị max của đoạn, nếu max <= 2 thì ta có thể bỏ qua đoạn đấy
void update(int id, int l, int r, int u, int v) {
if (l > v || r < u) return;
if (seg[id].mx <= 2) return;
if (l == r) {
a[l] = D[a[l]];
seg[id] = a[l];
return;
}
int mid = (l + r) >> 1;
update(id * 2, l, mid, u, v);
update(id * 2 + 1, mid + 1, r, u, v);
seg[id] = seg[id * 2] + seg[id * 2 + 1];
}
Node get(int id, int l, int r, int u, int v) {
if (l > v || r < u) return Node();
if (u <= l && r <= v) return seg[id];
int mid = (l + r) >> 1;
return get(id * 2, l, mid, u, v) + get(id * 2 + 1, mid + 1, r, u, v);
}
int main() {
ios::sync_with_stdio(false);
cin.tie(nullptr);
cin >> n >> q;
for (int i = 1; i <= n; i++) cin >> a[i];
sieve();
build(1, 1, n);
while (q--) {
int type, l, r;
cin >> type >> l >> r;
if (type == 1) {
update(1, 1, n, l, r);
}
else {
cout << get(1, 1, n, l, r).sum << '\n';
}
}
}
I2luY2x1ZGUgPGJpdHMvc3RkYysrLmg+Cgp1c2luZyBuYW1lc3BhY2Ugc3RkOyAgCgp0eXBlZGVmIGxvbmcgbG9uZyBsbDsgIAp0eXBlZGVmIHBhaXI8aW50LCBpbnQ+IGlpOyAgCgpjb25zdCBpbnQgSU5GID0gMWU5OyAgCmNvbnN0IGxsIExJTkYgPSAxZTE4OyAgCgpjb25zdCBpbnQgTiA9IDNlNSArIDU7ICAKY29uc3QgaW50IE1BWF9BID0gMWU2ICsgNTsgIAoKLy8gw50gdMaw4bufbmc6IMSQb8OhbiDEkcaw4bujYyBtYXgoe0QoYShpKSl9KSBz4bq9IGtow7RuZyBxdcOhIGzhu5tuIChzYXUga2hpIGNvZGUgxJHhu4MgY2hlY2sgdGjDrCB0YSBiaeG6v3QgxJHGsOG7o2MgduG7m2kgYShpKSA8PSAxZTYgdGjDrCBtYXgoe0QoYShpKSl9KSA8PSAyNDApCi8vIFThu6sgxJHDsywgdGEgY8OzIHRo4buDIGNvZGUgYnJ1dGUtZm9yY2UgxJHhu4MgcsO6dCByYSBuaOG6rW4geMOpdDoKLy8gVuG7m2kgYShpKSA8PSAxZTYgdGjDrCBt4buXaSBhKGkpIHThu5FpIMSRYSBjaOG7iSBi4buLIHTDoWMgxJHhu5luZyA2IGzhuqduCi8vIEtoaSBkw7luZyBTZWdtZW50IFRyZWUgdGjDrCDEkeG7mSBwaOG7qWMgdOG6oXAgxJHhu4MgdXBkYXRlIDEgduG7iyB0csOtIGzDoCBPKGxvZ24pCi8vID0+IE3hu5dpIHbhu4sgdHLDrSB04buRaSDEkWEgYuG7iyB0w6FjIMSR4buZbmcgNiBs4bqnbiA9PiBPKDYgKiBsb2duKSAKLy8gPT4gTeG6o25nIGPDsyBuIHBo4bqnbiB04butOiBPKDYgKiBubG9nbikKLy8gPT4gxJDhu5kgcGjhu6ljIHThuqFwOiBPKHFsb2duICsgNiAqIG5sb2duKSB+IE8oKHEgKyBuKWxvZ24pCnN0cnVjdCBOb2RlIHsKCWludCBteDsgCglsbCBzdW07CgkKCU5vZGUoKSB7CgkJbXggPSAtSU5GLCBzdW0gPSAwOyAgCgl9CgoJTm9kZShpbnQgeCkgewoJCW14ID0gc3VtID0geDsgIAoJfQoKCU5vZGUgb3BlcmF0b3IrKGNvbnN0IE5vZGUmIG90aGVyKSBjb25zdCB7CgkJTm9kZSBjOyAgCgkJYy5teCA9IG1heChteCwgb3RoZXIubXgpOyAKCQljLnN1bSA9IHN1bSArIG90aGVyLnN1bTsgCgkJcmV0dXJuIGM7IAoJfQp9OyAKCmludCBuLCBxOyAKaW50IGFbTl07IAppbnQgRFtNQVhfQV07IC8vIERbaV0gPSBT4buRIMaw4bubYyBj4bunYSBpIAoKdm9pZCBzaWV2ZSgpIHsKCWZvciAoaW50IGkgPSAxOyBpIDwgTUFYX0E7IGkrKykgewoJCWZvciAoaW50IGogPSBpOyBqIDwgTUFYX0E7IGogKz0gaSkgRFtqXSsrOyAKCX0KfQoKLy8gdm9pZCBicnV0ZSgpIHsKLy8gCWludCBteCA9IDA7ICAKLy8gCWZvciAoaW50IGkgPSAxOyBpIDwgTUFYX0E7IGkrKykgewovLyAJCWludCB0bXAgPSBpLCBjbnQgPSAwOyAgCi8vIAkJd2hpbGUgKERbdG1wXSA8IHRtcCkgdG1wID0gRFt0bXBdLCBjbnQrKzsKLy8gCQlteCA9IG1heChteCwgY250KTsgIAovLyAJfQovLyAJY291dCA8PCBteCA8PCAnXG4nOyAKLy8gfQoKTm9kZSBzZWdbNCAqIE5dOyAKCnZvaWQgYnVpbGQoaW50IGlkLCBpbnQgbCwgaW50IHIpIHsKCWlmIChsID09IHIpIHsKCQlzZWdbaWRdID0gTm9kZShhW2xdKTsgIAoJCXJldHVybjsgCgl9CglpbnQgbWlkID0gKGwgKyByKSA+PiAxOyAKCWJ1aWxkKGlkICogMiwgbCwgbWlkKTsgCglidWlsZChpZCAqIDIgKyAxLCBtaWQgKyAxLCByKTsgCglzZWdbaWRdID0gc2VnW2lkICogMl0gKyBzZWdbaWQgKiAyICsgMV07IAp9CgovLyDEkOG7gyBjaGVjayB0cm9uZyBt4buZdCDEkW/huqFuIGPDsyB04buTbiB04bqhaSB24buLIHRyw60gbsOgbyBj4bqnbiDEkcaw4bujYyB1cGRhdGUgbuG7r2EgaGF5IGtow7RuZyB0aMOsIAovLyB0YSBxdWFuIHTDom0gZ2nDoSB0cuG7iyBtYXggY+G7p2EgxJFv4bqhbiwgbuG6v3UgbWF4IDw9IDIgdGjDrCB0YSBjw7MgdGjhu4MgYuG7jyBxdWEgxJFv4bqhbiDEkeG6pXkgCnZvaWQgdXBkYXRlKGludCBpZCwgaW50IGwsIGludCByLCBpbnQgdSwgaW50IHYpIHsKCWlmIChsID4gdiB8fCByIDwgdSkgcmV0dXJuOyAgCglpZiAoc2VnW2lkXS5teCA8PSAyKSByZXR1cm47IAoJaWYgKGwgPT0gcikgewoJCWFbbF0gPSBEW2FbbF1dOyAgCgkJc2VnW2lkXSA9IGFbbF07IAoJCXJldHVybjsgIAoJfQoJaW50IG1pZCA9IChsICsgcikgPj4gMTsgCgl1cGRhdGUoaWQgKiAyLCBsLCBtaWQsIHUsIHYpOyAKCXVwZGF0ZShpZCAqIDIgKyAxLCBtaWQgKyAxLCByLCB1LCB2KTsgCglzZWdbaWRdID0gc2VnW2lkICogMl0gKyBzZWdbaWQgKiAyICsgMV07IAp9CgpOb2RlIGdldChpbnQgaWQsIGludCBsLCBpbnQgciwgaW50IHUsIGludCB2KSB7CglpZiAobCA+IHYgfHwgciA8IHUpIHJldHVybiBOb2RlKCk7IAoJaWYgKHUgPD0gbCAmJiByIDw9IHYpIHJldHVybiBzZWdbaWRdOyAKCWludCBtaWQgPSAobCArIHIpID4+IDE7IAoJcmV0dXJuIGdldChpZCAqIDIsIGwsIG1pZCwgdSwgdikgKyBnZXQoaWQgKiAyICsgMSwgbWlkICsgMSwgciwgdSwgdik7IAp9CgppbnQgbWFpbigpIHsKCWlvczo6c3luY193aXRoX3N0ZGlvKGZhbHNlKTsgCgljaW4udGllKG51bGxwdHIpOyAgCQoJY2luID4+IG4gPj4gcTsgCglmb3IgKGludCBpID0gMTsgaSA8PSBuOyBpKyspIGNpbiA+PiBhW2ldOyAgCgkJCQoJc2lldmUoKTsgICAKCglidWlsZCgxLCAxLCBuKTsgCgoJd2hpbGUgKHEtLSkgewoJCWludCB0eXBlLCBsLCByOyAKCQljaW4gPj4gdHlwZSA+PiBsID4+IHI7IAoKCQlpZiAodHlwZSA9PSAxKSB7CgkJCXVwZGF0ZSgxLCAxLCBuLCBsLCByKTsgCgkJfQoJCWVsc2UgewoJCQljb3V0IDw8IGdldCgxLCAxLCBuLCBsLCByKS5zdW0gPDwgJ1xuJzsgCgkJfQoJfQp9