using System; using System.Collections.Generic; using System.Diagnostics; using System.Linq; using System.Numerics; public class RangeSet where T : IMinMaxValue, IBinaryInteger { private SortedSet> Set; private T Inf; public Tuple Min { private set; get; } public Tuple Max { private set; get; } public RangeSet() { Inf = T.MaxValue / (T.One + T.One); Set = new SortedSet>(); Min = new Tuple(-Inf, -Inf); Max = new Tuple(Inf, Inf); Set.Add(Min); Set.Add(Max); } public bool Covered(T l, T r) { Debug.Assert(l <= r); return CoveredBy(l, r) != Min; } public bool Covered(T x) { return Covered(x, x); } // [l, r]がカバーされているなら,その区間を返す. されていないなら[-TINF,-TINF]を返す public Tuple CoveredBy(T l, T r) { Debug.Assert(l <= r); var range = Set.GetViewBetween(Min, Tuple.Create(l, Inf)).Max; return range.Item1 <= l && r <= range.Item2 ? range : Min; } public Tuple CoveredBy(T x) { return CoveredBy(x, x); } // insert[l,r], 増加量を返す public T Insert(T l, T r) { Debug.Assert(l <= r); var range = Set.GetViewBetween(Min, Tuple.Create(l, Inf)).Max; if (range.Item1 <= l && r <= range.Item2) { return T.Zero; } T sumErased = T.Zero; if (range.Item1 <= l && l <= range.Item2 + T.One) { l = range.Item1; sumErased += range.Item2 - range.Item1 + T.One; Set.Remove(range); } var view = Set.GetViewBetween(Tuple.Create(range.Item1 + T.One, Inf), Set.Max); var last = view.Min; var removes = new List>(); foreach (var x in view) { last = x; if (r <= x.Item2) { break; } sumErased += x.Item2 - x.Item1 + T.One; removes.Add(x); } foreach (var x in removes) { Set.Remove(x); } if (last.Item1 - T.One <= r && r <= last.Item2) { sumErased += last.Item2 - last.Item1 + T.One; r = last.Item2; Set.Remove(last); } Set.Add(Tuple.Create(l, r)); return (r - l + T.One) - sumErased; } public T Insert(T x) { return Insert(x, x); } // erase [l,r], 減少量を返す public T Erase(T l, T r) { Debug.Assert(l <= r); var range = Set.GetViewBetween(Min, Tuple.Create(l + T.One, Inf)).Max; if (range.Item1 <= l && r <= range.Item2) { // 完全に1つの区間に包含されている if (range.Item1 < l) { Set.Add(Tuple.Create(range.Item1, l - T.One)); } if (r < range.Item2) { Set.Add(Tuple.Create(r + T.One, range.Item2)); } Set.Remove(range); return r - l + T.One; } T ret = T.Zero; if (range.Item1 <= l && l <= range.Item2) { ret += range.Item2 - l + T.One; if (range.Item1 < l) { Set.Add(Tuple.Create(range.Item1, l - T.One)); } Set.Remove(range); } var view = Set.GetViewBetween(Tuple.Create(range.Item1 + T.One, Inf), Set.Max); var last = view.Min; foreach (var x in view) { last = x; if (x.Item2 > r) { break; } ret += x.Item2 - x.Item1 + T.One; Set.Remove(x); } // 右端が区間の間にあるか if (last.Item1 <= r && r <= last.Item2) { ret += r - last.Item1 + T.One; if (r < last.Item2) { Set.Add(Tuple.Create(r + T.One, last.Item2)); } Set.Remove(last); } return ret; } public T Erase(T x) { return Erase(x, x); } public int Size() { return Set.Count - 2; } public override string ToString() { return string.Join(", ", Set.Select(x => $"[{x.Item1},{x.Item2}]")); } } public static class Solution { public static void Main() { var vals = Console.ReadLine().Split(' ').Select(long.Parse).ToArray(); var D = vals[0]; var Q = vals[1]; var set = new RangeSet(); var answer = new List(); long max = 0; for (int q = 0; q < Q; q++) { vals = Console.ReadLine().Split(' ').Select(long.Parse).ToArray(); var A = vals[0]; var B = vals[1]; set.Insert(A, B); var range = set.CoveredBy(A); var len = range == set.Min ? 0 : range.Item2 - range.Item1 + 1; max = Math.Max(max, len); answer.Add(max); } Console.WriteLine(string.Join(Environment.NewLine, answer)); } }