#include <bits/stdc++.h>
using
namespace
std;
#define MAX 1000000
#define MOD 1000000007
#define ll long long int
int
block;
struct
Query {
int
L, R;
};
vector<pair<
int
,
int
> > store[MAX + 1];
int
counter[MAX + 1] = {};
int
result = 1;
ll inverse[MAX + 1];
bool
compare(Query x, Query y)
{
if
(x.L / block != y.L / block)
return
x.L / block < y.L / block;
return
x.R < y.R;
}
void
modularInverse()
{
inverse[0] = inverse[1] = 1;
for
(
int
i = 2; i <= MAX; i++)
inverse[i] = inverse[MOD % i]
* (MOD - MOD / i)
% MOD;
}
void
sieve()
{
store[1].push_back({ 1, 0 });
for
(
int
i = 2; i <= MAX; i++)
{
if
(store[i].size() == 0)
{
store[i].push_back({ i, 1 });
for
(
int
j = 2 * i; j <= MAX; j += i)
{
int
cnt = 0;
int
x = j;
while
(x % i == 0)
cnt++, x /= i;
store[j].push_back({ i, cnt });
}
}
}
}
void
add(
int
currL,
int
a[])
{
int
value = a[currL];
for
(
auto
it = store[value].begin();
it != store[value].end(); it++) {
int
prev = counter[it->first];
counter[it->first] += it->second;
result = (result * inverse[prev + 1])
% MOD;
result = (result *
(counter[it->first] + 1))
% MOD;
}
}
void
remove
(
int
currR,
int
a[])
{
int
value = a[currR];
for
(
auto
it = store[value].begin();
it != store[value].end(); it++) {
int
prev = counter[it->first];
counter[it->first] -= it->second;
result = (result * inverse[prev + 1])
% MOD;
result = (result *
(counter[it->first] + 1))
% MOD;
}
}
void
queryResults(
int
a[],
int
n, Query q[],
int
m)
{
block = (
int
)
sqrt
(n);
sort(q, q + m, compare);
int
currL = 0, currR = 0;
for
(
int
i = 0; i < m; i++) {
int
L = q[i].L, R = q[i].R;
while
(currR <= R) {
add(currR, a);
currR++;
}
while
(currL > L) {
add(currL - 1, a);
currL--;
}
while
(currR > R + 1)
{
remove
(currR - 1, a);
currR--;
}
while
(currL < L) {
remove
(currL, a);
currL++;
}
cout << result << endl;
}
}
int
main()
{
sieve();
modularInverse();
int
a[] = { 5, 2, 3, 1, 4 };
int
n =
sizeof
(a) /
sizeof
(a[0]);
Query q[] = { { 1, 3 }, { 0, 4 } };
int
m =
sizeof
(q) /
sizeof
(q[0]);
queryResults(a, n, q, m);
return
0;
}