#include <iostream>
#include <cstdio>
#include <cstring>
#include <vector>
#include <algorithm>
#include <cstdlib>
// Accepted 4868K 3016MS C++ 2390B 2013-08-09 12:45:26
// Accepted 5392K 4844MS G++ 2390B 2013-08-09 12:44:44
using namespace std;
const int maxn = 50100;
const int INF = 0x7fffffff;
struct Node {
int Left, Right;
int maxval, minxval;
Node *LeftChild, *RightChild;
Node() {
maxval = -1;//保證插入時候更新不會出錯。
minxval = INF;
}
};
int ql, qr;//全局變量,即每次插入或查詢區間。
int Min, Max;//保存要查詢區間的最值.
int n, m;
Node *root = NULL;
void Build(Node* cur, int L, int R) {
cur->Left = L;
cur->Right = R;
if(L != R) {
cur->LeftChild = new Node;
cur->RightChild = new Node;
Build(cur->LeftChild, L, (L+R)/2);
Build(cur->RightChild, (L+R)/2+1, R);
}
else {//L == R
cur->LeftChild = NULL;//沒有左右孩子。
cur->RightChild = NULL;
}
}
//插入時候每次給ql賦值.
void update(Node* cur, int L, int R, int value) {
if(L==R && L == ql) { //葉子節點。
cur->maxval = value;
cur->minxval = value;
return;
}
Node* LC = cur->LeftChild;
Node* RC = cur->RightChild;
int M = (L+R)/2;
if(ql <= M) update(LC, L, M, value);
else update(RC, M+1, R, value);
cur->maxval = max(LC->maxval, RC->maxval);
cur->minxval = min(LC->minxval, RC->minxval);
}
//區間:[ql, qr], Min, Max 全局變量, 進行初始化。
void query(Node* cur, int L, int R) {
if(ql <= L && R <= qr) {
Min = min(Min, cur->minxval);
Max = max(Max, cur->maxval);
return;
}
Node* LC = cur->LeftChild;
Node* RC = cur->RightChild;
int M = (L+R)/2;
if(ql <= M) query(LC, L, M);
if(qr > M) query(RC, M+1, R);
return;
}
void init(){
int tmp;
Max = -1;//littl, import;
Min = 10000000;//big
Build(root, 1, n);
for(int i = 1; i <= n; i++) {
scanf("%d", &tmp);
ql = i;
update(root, 1, n, tmp);
}
}
int main()
{
int start, endx;
while(scanf("%d%d", &n, &m) != EOF) {
root = new Node;
init();
for(int i = 1; i <= m; i++) {
scanf("%d%d", &start, &endx);
ql = start, qr = endx;
Max = -1, Min = INF;
query(root, 1, n);
int res = Max - Min;
printf("%d\n", res);
}
}
return 0;
}