[Solution]
Simply modify some important positions by map or balanced tree. For each fence, remove all the nodes between a[i] and b[i]. Then add two new nodes on a[i] and b[i]. Each node will only be inserted and poped once. The total time complex is O(n lg n). It's very easy to code.
[Code]
#include <cstdio>
#include <cctype>
#include <memory.h>
#include <algorithm>
using namespace std;
typedef long long qw;
#ifdef WIN32
#define lld "%I64d"
#else
#define lld "%lld"
#endif
int nextInt() {
int s = 0, d;
bool flag = 0;
do {
d = getchar();
if (d == '-')
flag = 1;
} while (!isdigit(d));
do
s = s * 10 + d - 48, d = getchar();
while (isdigit(d));
return flag ? -s : s;
}
const int maxn = 200009;
const qw qwinf = 0x3f3f3f3f3f3f3f3f;
const int intinf = 0x3f3f3f3f;
class sbt {
private:
int root, ls[maxn], rs[maxn], sz[maxn], key[maxn];
int nst[maxn], tnst;
qw val[maxn], ansl, ansr;
inline void update(const int& p) {
sz[p] = sz[ls[p]] + sz[rs[p]] + 1;
}
inline void lRot(int& p) {
int q = rs[p];
if (!q)
return;
rs[p] = ls[q];
ls[q] = p;
update(p);
update(q);
p = q;
}
inline void rRot(int& p) {
int q = ls[p];
if (!q)
return;
ls[p] = rs[q];
rs[q] = p;
update(p);
update(q);
p = q;
}
void maintain(int& p, bool flag) {
if (flag) {
if (sz[ls[p]] + 1 > sz[rs[p]])
rRot(p);
}
else
if (sz[ls[p]] < sz[rs[p]] + 1)
lRot(p);
}
void ins(int& p, int k0, qw v0) {
if (!p) {
p = nst[-- tnst];
ls[p] = 0;
rs[p] = 0;
sz[p] = 1;
key[p] = k0;
val[p] = v0;
}
else if (key[p] == k0)
val[p] = min(val[p], v0);
else {
if (k0 < key[p])
ins(ls[p], k0, v0);
else
ins(rs[p], k0, v0);
update(p);
maintain(p, k0 < key[p]);
}
}
void del(int& p, int k0) {
if (key[p] == k0) {
if (!ls[p] || !rs[p])
nst[tnst ++] = p;
if (!ls[p])
p = rs[p];
else if (!rs[p])
p = ls[p];
else {
int q = ls[p];
while (rs[q])
q = rs[q];
key[p] = key[q];
val[p] = val[q];
del(ls[p], key[p]);
if (p)
update(p);
}
}
else {
if (k0 < key[p])
del(ls[p], k0);
else
del(rs[p], k0);
if (p)
update(p);
}
}
void ers(int& p, int l, int r) {
while (p && key[p] >= l && key[p] <= r) {
ansl = min(ansl, val[p] + key[p] - l);
ansr = min(ansr, val[p] + r - key[p]);
del(p, key[p]);
}
if (p && l < key[p])
ers(ls[p], l, r);
if (p && r > key[p])
ers(rs[p], l, r);
if (p)
update(p);
}
qw getAns(int p) {
if (!p)
return qwinf;
else
return min(val[p] + abs(key[p]), min(getAns(ls[p]), getAns(rs[p])));
}
public:
void init() {
root = 0;
sz[0] = 0;
tnst = 0;
for (int i = 1; i < maxn; i ++)
nst[tnst ++] = i;
}
void insert(int k0, qw v0) {
ins(root, k0, v0);
}
void erase(int l0, int r0, qw& sl, qw& sr) {
ansl = qwinf;
ansr = qwinf;
ers(root, l0, r0);
sl = ansl;
sr = ansr;
}
int minKey() {
int p = root;
while (ls[p])
p = ls[p];
return p ? key[p] : intinf;
}
int maxKey() {
int p = root;
while (rs[p])
p = rs[p];
return p ? key[p] : -intinf;
}
qw getAns() {
return getAns(root);
}
int size() {
return sz[root];
}
void disp(int p = -1) {
if (p == -1)
p = root;
if (!p)
return;
disp(ls[p]);
printf("%3d:%6lld\n", key[p], val[p]);
disp(rs[p]);
}
};
sbt t;
int n, p0, a[maxn], b[maxn];
int main() {
#ifndef ONLINE_JUDGE
freopen("in.txt", "r", stdin);
#endif
t. init();
n = nextInt();
p0 = nextInt();
for (int i = 1; i <= n; i ++) {
a[i] = nextInt();
b[i] = nextInt();
}
t. insert(p0, 0);
for (int i = n; i; i --) {
if (a[i] >= t. maxKey() || b[i] <= t. minKey())
continue;
qw ansl, ansr;
t. erase(a[i], b[i], ansl, ansr);
t. insert(a[i], ansl);
t. insert(b[i], ansr);
}
printf(lld "\n", t. getAns());
}