#include using namespace std; const int N = 2e5 + 5, INF = 1e9; int n, m, q, val[N]; int mx[4 * N]; long long sum[4 * N]; vector < pair < int, int > > g[N]; long long ans[N]; // link cut tree class LCT { public: int ch[N][2], fa[N], val[N], mn[N]; bool rev[N]; LCT() { for (int i = 1; i < N; i++) { val[i] = mn[i] = INF; } } bool which(int x) { return ch[fa[x]][1] == x; } bool isRoot(int x) { return ch[fa[x]][0] != x && ch[fa[x]][1] != x; } void upd_vertex(int x){ mn[x] = val[x]; if (ch[x][0]) mn[x] = min(mn[x], mn[ch[x][0]]); if (ch[x][1]) mn[x] = min(mn[x], mn[ch[x][1]]); } void reverse(int x) { swap(ch[x][0], ch[x][1]); rev[x] ^= true; } void pushdown1(int x) { if (!rev[x]) return; if (ch[x][0]) reverse(ch[x][0]); if (ch[x][1]) reverse(ch[x][1]); rev[x] = 0; } void pushdown(int x){ if (!isRoot(x)) pushdown(fa[x]); pushdown1(x); } void rotate(int x) { bool dir = which(x); int f = fa[x]; if (!isRoot(f)) ch[fa[f]][which(f)] = x; fa[x] = fa[f]; fa[f] = x; if (ch[x][dir ^ 1]) fa[ch[x][dir ^ 1]] = f; ch[f][dir] = ch[x][dir ^ 1]; ch[x][dir ^ 1] = f; upd_vertex(f); upd_vertex(x); } void splay(int x) { pushdown(x); for (int f = fa[x]; !isRoot(x); f = fa[x]){ if (!isRoot(f)) { rotate(which(f) == which(x) ? f : x); } rotate(x); } upd_vertex(x); } void access(int x){ for (int last = 0; x; last = x, x = fa[x]){ splay(x); ch[x][1] = last; upd_vertex(x); } } void make_rt(int x){ access(x); splay(x); reverse(x); } bool connected(int x, int y) { if (x == y) return true; make_rt(x); access(y); splay(y); return fa[x]; } void link(int x, int y) { make_rt(x); fa[x] = y; access(x); splay(x); } void cut(int x, int y) { make_rt(x); access(y); splay(y); fa[x] = 0; ch[y][0] = 0; upd_vertex(y); } int query(int x, int y) { make_rt(x); access(y); splay(y); return mn[y]; } }; inline long long my_get(int x) { return x * 1LL * (x + 1) / 2; } inline long long my_get(int l, int r) { return my_get(r) - my_get(l - 1); } void build(int v, int l, int r) { if (l == r) { mx[v] = sum[v] = val[l]; return; } int mid = (r + l) >> 1; build(v + v, l, mid); build(v + v + 1, mid + 1, r); mx[v] = max(mx[v + v], mx[v + v + 1]); sum[v] = sum[v + v] + sum[v + v + 1]; } int get_sum(int v, int l, int r, int tl, int tr) { if (l > r || tl > tr || l > tr || tl > r) return 0; if (tl <= l && r <= tr) return sum[v]; int mid = (r + l) >> 1; return get_sum(v + v, l, mid, tl, tr) + get_sum(v + v + 1, mid + 1, r, tl, tr); } int get_pos(int v, int l, int r, int tl, int tr, int val) { if (l > r || l > tr || tl > r || mx[v] <= val) return -1; if (l == r) return l; int mid = (r + l) >> 1; int y = get_pos(v + v, l, mid, tl, tr, val); if (y == -1) y = get_pos(v + v + 1, mid + 1, r, tl, tr, val); return y; } int main() { ios_base::sync_with_stdio(0);cin.tie(0);cout.tie(0); cin >> n >> m; LCT lct; for (int i = 1; i <= m; i++) { int x, y; cin >> x >> y; val[i] = val[i - 1]; lct.val[i + n] = i; if (lct.connected(x, y)){ int res = lct.query(x, y); lct.cut(x, n + res); lct.cut(y, n + res); lct.link(x, n + i); lct.link(y, n + i); val[i] = max(val[i], res); } else{ lct.link(x, n + i); lct.link(y, n + i); } } cin >> q; for (int i = 1; i <= q; i++) { int l, r; cin >> l >> r; g[r].push_back(make_pair(l, i)); } build(1, 1, m); for (int i = 1; i <= m; i++) { for (auto it : g[i]) { int l = it.first, r = i; int len = r - l + 1; int pos = get_pos(1, 1, m, l, r, l - 1); long long res = 0; if (pos == -1) { res = len * (l - 1); } else { res = (pos - l) * (l - 1) + get_sum(1, 1, m, pos, r); } ans[it.second] = my_get(l, r) - res; } } for (int i = 1; i <= q; i++) cout << ans[i] << "\n"; }