They say "years are like dominoes, tumbling one after the other". But would a year fit into a grid? I don't think so.Limak is a little polar bear who loves to play. He has recently got a rectangular grid with h rows and w columns. Each cell is a square, either empty (denoted by '.') or forbidden (denoted by '#'). Rows are numbered 1 through h from top to bottom. Columns are numbered 1 through w from left to right.Also, Limak has a single domino. He wants to put it somewhere in a grid. A domino will occupy exactly two adjacent cells, located either in one row or in one column. Both adjacent cells must be empty and must be inside a grid.Limak needs more fun and thus he is going to consider some queries. In each query he chooses some rectangle and wonders, how many way are there to put a single domino inside of the chosen rectangle?

The first line of the input contains two integers h and w (1 ≤ h, w ≤ 500) – the number of rows and the number of columns, respectively. The next h lines describe a grid. Each line contains a string of the length w. Each character is either '.' or '#' — denoting an empty or forbidden cell, respectively. The next line contains a single integer q (1 ≤ q ≤ 100 000) — the number of queries. Each of the next q lines contains four integers r1i, c1i, r2i, c2i (1 ≤ r1i ≤ r2i ≤ h, 1 ≤ c1i ≤ c2i ≤ w) — the i-th query. Numbers r1i and c1i denote the row and the column (respectively) of the upper left cell of the rectangle. Numbers r2i and c2i denote the row and the column (respectively) of the bottom right cell of the rectangle.

Print q integers, i-th should be equal to the number of ways to put a single domino inside the i-th rectangle.

NoteA red frame below corresponds to the first query of the first sample. A domino can be placed in 4 possible ways.

import std.stdio, std.array, std.string, std.conv, std.algorithm;
import std.typecons, std.range, std.random, std.math, std.container;
import std.numeric, std.bigint, core.bitop, core.stdc.stdio, std.bitmanip;

void main() {
    auto s = readln.split.map!(to!int);
    auto H = s[0];
    auto W = s[1];

    auto B = new string[](H);
    foreach (i; 0..H) B[i] = readln.chomp;

    auto yoko = new int[][](H+1, W+1);
    auto tate = new int[][](H+1, W+1);
    foreach (i; 0..H) {
        foreach (j; 0..W) {
            if (j < W-1 && B[i][j] == '.' && B[i][j+1] == '.')
                yoko[i+1][j+1] += 1;
            if (i < H-1 && B[i][j] == '.' && B[i+1][j] == '.')
                tate[i+1][j+1] += 1;
        }
    }

    foreach (i; 0..H) foreach (j; 1..W) {
            yoko[i+1][j+1] += yoko[i+1][j];
            tate[i+1][j+1] += tate[i+1][j];
        }
    foreach (j; 0..W) foreach (i; 1..H) {
            yoko[i+1][j+1] += yoko[i][j+1];
            tate[i+1][j+1] += tate[i][j+1];
        }

    int acm(int a, int b, int c, int d) {
        return
            yoko[c][d-1] - yoko[a-1][d-1] - yoko[c][b-1] + yoko[a-1][b-1] +
            tate[c-1][d] - tate[a-1][d] - tate[c-1][b-1] + tate[a-1][b-1];
    }

    auto M = readln.chomp.to!int;
    foreach (_; 0..M) {
        int ans = 0;
        s = readln.split.map!(to!int);
        writeln(acm(s[0], s[1], s[2], s[3]));
    }
}

import std.algorithm;
import std.array;
import std.container;
import std.conv;
import std.exception;
import std.functional;
import std.math;
import std.numeric;
import std.range;
import std.stdio;
import std.string;
import std.typecons;
import core.bitop;

void main ()
{
	int h, w;
	while (readf (" %s %s", &h, &w) > 0)
	{
		readln;
		string [] a;
		a ~= '#'.repeat (w + 2).array;
		foreach (row; 1..h + 1)
		{
			a ~= '#' ~ readln.strip ~ '#';
		}
		a ~= '#'.repeat (w + 2).array;

		auto frow = new int [] [] (h + 2, w + 2);
		foreach (row; 0..h + 2)
		{
			frow[row][0] = 0;
			foreach (col; 1..w + 2)
			{
				frow[row][col] = frow[row][col - 1] +
				    (a[row][col - 1] == '.' &&
				    a[row][col] == '.');
			}
		}

		auto fcol = new int [] [] (w + 2, h + 2);
		foreach (col; 0..w + 2)
		{
			fcol[col][0] = 0;
			foreach (row; 1..h + 2)
			{
				fcol[col][row] = fcol[col][row - 1] +
				    (a[row - 1][col] == '.' &&
				    a[row][col] == '.');
			}
		}

		int q;
		readf (" %s", &q);
		foreach (z; 0..q)
		{
			int row1, col1, row2, col2;
			readf (" %s %s %s %s", &row1, &col1, &row2, &col2);
			int res = 0;
			foreach (row; row1..row2 + 1)
			{
				res += frow[row][col2] - frow[row][col1];
			}
			foreach (col; col1..col2 + 1)
			{
				res += fcol[col][row2] - fcol[col][row1];
			}
			writeln (res);
		}
	}
}


Writing light novels is the most important thing in Linova's life. Last night, Linova dreamed about a fantastic kingdom. She began to write a light novel for the kingdom as soon as she woke up, and of course, she is the queen of it. There are $$$n$$$ cities and $$$n-1$$$ two-way roads connecting pairs of cities in the kingdom. From any city, you can reach any other city by walking through some roads. The cities are numbered from $$$1$$$ to $$$n$$$, and the city $$$1$$$ is the capital of the kingdom. So, the kingdom has a tree structure.As the queen, Linova plans to choose exactly $$$k$$$ cities developing industry, while the other cities will develop tourism. The capital also can be either industrial or tourism city.A meeting is held in the capital once a year. To attend the meeting, each industry city sends an envoy. All envoys will follow the shortest path from the departure city to the capital (which is unique).Traveling in tourism cities is pleasant. For each envoy, his happiness is equal to the number of tourism cities on his path.In order to be a queen loved by people, Linova wants to choose $$$k$$$ cities which can maximize the sum of happinesses of all envoys. Can you calculate the maximum sum for her?

The first line contains two integers $$$n$$$ and $$$k$$$ ($$$2\le n\le 2 \cdot 10^5$$$, $$$1\le k< n$$$)  — the number of cities and industry cities respectively. Each of the next $$$n-1$$$ lines contains two integers $$$u$$$ and $$$v$$$ ($$$1\le u,v\le n$$$), denoting there is a road connecting city $$$u$$$ and city $$$v$$$. It is guaranteed that from any city, you can reach any other city by the roads.

Print the only line containing a single integer  — the maximum possible sum of happinesses of all envoys.

NoteIn the first example, Linova can choose cities $$$2$$$, $$$5$$$, $$$6$$$, $$$7$$$ to develop industry, then the happiness of the envoy from city $$$2$$$ is $$$1$$$, the happiness of envoys from cities $$$5$$$, $$$6$$$, $$$7$$$ is $$$2$$$. The sum of happinesses is $$$7$$$, and it can be proved to be the maximum one.In the second example, choosing cities $$$3$$$, $$$4$$$ developing industry can reach a sum of $$$3$$$, but remember that Linova plans to choose exactly $$$k$$$ cities developing industry, then the maximum sum is $$$2$$$.

import core.bitop, std.bitmanip;
import core.checkedint;
import std.algorithm, std.functional, std.meta;
import std.array, std.container;
import std.bigint;
import std.conv;
import std.math, std.numeric;
import std.range, std.range.interfaces;
import std.stdio, std.string;
import std.typecons;

void main()
{
    int n, k;
    readf("%s %s", &n, &k);
    readln;

    auto g = new int[][] (n+1);
    foreach (i; 0 .. n-1) {
        int u, v;
        readf("%s %s", &u, &v);
        readln;

        g[u] ~= v;
        g[v] ~= u;
    }

    auto depth = new int[] (n+1);
    auto sz = new int[] (n+1);
    auto parent = new int[] (n+1);
    auto isLeaf = new bool[] (n+1);
    auto gain = new int[] (n+1);

    void dfs(int v, int fr) {
        depth[v] = v == 1 ? 0 : depth[fr] + 1;
        sz[v] = 1;
        parent[v] = fr;
        isLeaf[v] = true;

        foreach (u; g[v]) {
            if (u == fr) { continue; }

            dfs(u, v);

            sz[v] += sz[u];
            isLeaf[v] = false;
        }

        gain[v] = depth[v] - (sz[v] - 1);
    }

    dfs(1, 0);

    auto leavesWithGain = (n+1).iota.filter!(i => isLeaf[i]).map!(i => tuple(gain[i], i));
    auto rbt = redBlackTree(leavesWithGain);

    auto ans = 0L;
    while (k--) {
        ans += rbt.back[0];
        auto v = rbt.back[1];
        rbt.removeBack();

        rbt.insert(tuple(gain[parent[v]], parent[v]));
    }

    ans.writeln;
}

import core.bitop, std.bitmanip;
import core.checkedint;
import std.algorithm, std.functional, std.meta;
import std.array, std.container;
import std.bigint;
import std.conv;
import std.math, std.numeric;
import std.range, std.range.interfaces;
import std.stdio, std.string;
import std.typecons;

void main()
{
    int n, k;
    readf("%s %s", &n, &k);
    readln;

    auto g = new int[][] (n+1);
    foreach (i; 0 .. n-1) {
        int u, v;
        readf("%s %s", &u, &v);
        readln;

        g[u] ~= v;
        g[v] ~= u;
    }

    auto depth = new int[] (n+1);
    auto sz = new int[] (n+1);
    auto parent = new int[] (n+1);
    auto isLeaf = new bool[] (n+1);
    auto gain = new int[] (n+1);

    void dfs(int v, int fr) {
        depth[v] = v == 1 ? 0 : depth[fr] + 1;
        sz[v] = 1;
        parent[v] = fr;
        isLeaf[v] = true;

        foreach (u; g[v]) {
            if (u == fr) { continue; }

            dfs(u, v);

            sz[v] += sz[u];
            isLeaf[v] = false;
        }

        gain[v] = depth[v] - (sz[v] - 1);
    }

    dfs(1, 0);

    auto leavesWithGain = (n+1).iota.filter!(i => isLeaf[i]).map!(i => tuple(gain[i], i));
    auto rbt = redBlackTree(leavesWithGain);
    foreach (i; 1 .. n+1) {
        if (isLeaf[i]) { rbt.insert(tuple(gain[i], i)); }
    }

    auto ans = 0L;
    while (k--) {
        ans += rbt.back[0];
        auto v = rbt.back[1];
        rbt.removeBack();

        rbt.insert(tuple(gain[parent[v]], parent[v]));
    }

    ans.writeln;
}

/// https://codeforces.com/contest/1336/problem/A
import std.stdio;
import std.array;
import std.algorithm;
import std.container;
import std.range : sequence, take;

void main()
{
  int n, k;
  stdin.readf!"%d %d\n"(n, k);

  int[][] adj;  adj.length = n+1;

  int u, v;
  for (int i=1; i<n; i++) {
    stdin.readf!"%d %d\n"(u, v);
    adj[u] ~= v;
    adj[v] ~= u;
  }

  int[] depth; depth.length = n+1;
  int[] childCount; childCount.length = n+1;
  int dfs(int node, int parent=0, int _depth=0) {
    int children = 0;
    foreach (neighbor; adj[node]) {
      if (neighbor != parent)
        children += dfs(neighbor, node, _depth+1);
    }
    depth[node] = _depth;
    childCount[node] = children;
    return children+1;
  }
  dfs(1);

  int prioriry(int node) { return depth[node] - childCount[node]; }
  bool compare(int a, int b) { return prioriry(a) < prioriry(b); }
  auto nodes = sequence!"n+1"().take(n).array;
  auto minHeap = heapify!compare(nodes);

  long happiness;
  foreach (city; minHeap.take(k))
    happiness += prioriry(city);

  writeln(happiness);
}

import std.stdio      : stdin, writeln;
import std.algorithm  : fold, sum;
import std.container  : heapify;
import std.range      : sequence, take;

void main()
{
  int n, k;
  stdin.readf!"%d %d\n"(n, k);

  int[][] adj;
  long[] prioriry;
  adj.length = prioriry.length = n;

  int u, v;
  for (int i=1; i<n; i++) {
    stdin.readf!"%d %d\n"(u, v);
    u--; v--;
    adj[u] ~= v;
    adj[v] ~= u;
  }

  int dfs(int node, int parent=0, int depth=0) {
    auto children = adj[node].fold!((ac,n) => ac + (n != parent? dfs(n,node,depth+1): 0))(0);
    prioriry[node] = depth - children;
    return children + 1;
  }
  dfs(0);

  writeln(heapify(prioriry).take(k).sum);
}

import std.algorithm;
import std.conv;
import std.range;
import std.stdio;
import std.string;
import std.typecons;

void main ()
{
	int n, k;
	while (readf !(" %s %s") (n, k) > 0)
	{
		auto a = new int [] [n];
		foreach (i; 0..n - 1)
		{
			int u, v;
			readf !(" %s %s") (u, v);
			u -= 1;
			v -= 1;
			a[u] ~= v;
			a[v] ~= u;
		}

		auto f = new int [n];

		int recur (int v, int p, int depth)
		{
			int total = 0;
			foreach (u; a[v])
			{
				if (u != p)
				{
					total += recur (u, v, depth + 1);
				}
			}
			f[v] = depth - total;
			return total + 1;
		}

		recur (0, -1, 0);
		sort !(q{a > b}) (f);
		writeln (sum (f[0..k], 0L));
	}
}

import std.conv, std.functional, std.range, std.stdio, std.string;
import std.algorithm, std.array, std.bigint, std.bitmanip, std.complex, std.container, std.math, std.mathspecial, std.numeric, std.regex, std.typecons;
import core.bitop;

class EOFException : Throwable { this() { super("EOF"); } }
string[] tokens;
string readToken() { for (; tokens.empty; ) { if (stdin.eof) { throw new EOFException; } tokens = readln.split; } auto token = tokens.front; tokens.popFront; return token; }
int readInt() { return readToken.to!int; }
long readLong() { return readToken.to!long; }
real readReal() { return readToken.to!real; }

bool chmin(T)(ref T t, in T f) { if (t > f) { t = f; return true; } else { return false; } }
bool chmax(T)(ref T t, in T f) { if (t < f) { t = f; return true; } else { return false; } }

int binarySearch(alias pred, T)(in T[] as) { int lo = -1, hi = cast(int)(as.length); for (; lo + 1 < hi; ) { const mid = (lo + hi) >> 1; (unaryFun!pred(as[mid]) ? hi : lo) = mid; } return hi; }
int lowerBound(T)(in T[] as, T val) { return as.binarySearch!(a => (a >= val)); }
int upperBound(T)(in T[] as, T val) { return as.binarySearch!(a => (a > val)); }

int N, K;
int[] A, B;

int[][] G;
int[] par, dep, sz;

void dfs(int u, int p) {
  par[u] = p;
  dep[u] = (p == -1) ? 0 : (dep[p] + 1);
  sz[u] = 1;
  foreach (i; G[u]) {
    const v = A[i] ^ B[i] ^ u;
    if (v != p) {
      dfs(v, u);
      sz[u] += sz[v];
    }
  }
}

void main() {
  try {
    for (; ; ) {
      N = readInt();
      K = readInt();
      A = new int[N - 1];
      B = new int[N - 1];
      foreach (i; 0 .. N - 1) {
        A[i] = readInt() - 1;
        B[i] = readInt() - 1;
      }

      G = new int[][N];
      foreach (i; 0 .. N - 1) {
        G[A[i]] ~= i;
        G[B[i]] ~= i;
      }
      par = new int[N];
      dep = new int[N];
      sz = new int[N];
      dfs(0, -1);

      auto degs = new int[N];
      foreach (u; 1 .. N) {
        ++degs[par[u]];
      }
      alias Entry = Tuple!(int, "score", int, "u");
      BinaryHeap!(Array!Entry) que;
      foreach (u; 1 .. N) {
        if (degs[u] == 0) {
          que.insert(Entry(dep[u], u));
        }
      }

      long ans;
      foreach (k; 0 .. K) {
        const e = que.front;
        que.removeFront;
        debug {
          writeln("e = ", e);
        }
        ans += e.score;
        const p = par[e.u];
        if (p != 0 && --degs[p] == 0) {
          que.insert(Entry(dep[p] - (sz[p] - 1), p));
        }
      }
      writeln(ans);
    }
  } catch (EOFException e) {
  }
}

import std.container;
import std.algorithm;
import std.range;
import std.array;
import std.stdio;
import std.utf;
import std.math;
import std.typecons;

alias type = single;
struct TestCase
{
  mixin prettyPrinting;

  long n, k;
  @Dim("n - 1") long[2][] edges;

  void solve(long tc = -1)
  {
    auto alist = makeSlice!(long[])(n);
    auto height = makeSlice!(long)(n);
    auto size = makeSlice!(long)(n);
    foreach(ref edge; edges)
      {
        edge[] -= 1;
        alist.at(edge[0]) ~= edge[1];
        alist.at(edge[1]) ~= edge[0];
      }
    void dfs(long node, long parent, long h)
    {
      height.at(node) = h;
      size.at(node) = 1;
      foreach(nei; alist.at(node))
        if (nei != parent)
          {
            dfs(nei, node, h + 1);
            size.at(node) += size.at(nei);
          }
    }
    dfs(0, -1, 0);
    long[] priol;
    foreach(node; 0 .. n)
      priol ~= height.at(node) - size.at(node) + 1;
    sort(priol);
    writeln(priol[$ - cast(size_t) k .. $].sum);
  }
}

struct Interval
{
  long l, h;

  bool empty()
  {
    return l > h;
  }
}

Interval intersect(Interval a, Interval b)
{
  return Interval(max(a.l, b.l), min(a.h, b.h));
}

struct If
{
  string condition;
}
enum ignore = If("false");
struct Dim
{
  string dimensions;
  int levels;
  this(string dimensions)
  {
    this.dimensions = dimensions;
    levels = cast(int)dimensions.count(",") + 1;
  }
}

template getArrayLevel(W)
{
  static if (isDynamicArray!W && !is(W == string))
    enum getArrayLevel = 1 + getArrayLevel!(removeArray!(W, 1));
  else
    enum getArrayLevel = 0;
}

static foreach(fieldName; 'a' .. cast(char)('z' + 1))
  {
    static if (fieldName != 'o')
      mixin("enum d", fieldName, " = Dim(\"", fieldName, "\");");
  }

mixin template prettyPrinting()
{
  string toString()
  {
    alias structType = typeof(this);
    auto res = appender!(string)();
    res.put(structType.stringof);
    res.put("(");
    static foreach(fieldName; FieldNameTuple!structType)
      {
        res.put(text(" ", fieldName, ": ", mixin(fieldName)));
      }
    res.put(" )");
    res.put("\n");
    return res[];
  }
}

struct Graph(N)
{
  size_t size;
  this(S)(S size)
  {
    adjacencyList.length = cast(size_t) size;
    this.size = cast(size_t) size;
    this.visited = makeSlice!bool(size);
  }
  N[][] adjacencyList;
  alias ne = neighbours;
  N[] neighbours(N n)
  {
    return adjacencyList.at(n);
  }
  alias bcon = biconnect;
  void biconnect(N a, N b)
  {
    adjacencyList.at(a) ~= b;
    adjacencyList.at(b) ~= a;
  }
  alias con = connect;
  void connect(N a, N b)
  {
    adjacencyList.at(a) ~= b;
  }
  void connect(R)(R edges)
  {
    foreach(ref edge; edges)
      {
        connect(edge[0], edge[1]);
      }
  }
  void biconnect(R)(R edges)
  {
    foreach(ref edge; edges)
      {
        biconnect(edge[0], edge[1]);
      }
  }
  alias deg = degree!long;
  auto degree(T)(N a)
  {
    return cast(T) adjacencyList.at(a).length;
  }

  auto visited = new bool[0];
  void dfs(Visitor)(long startNode)
  {
    auto visitor = Visitor.init;
    void internalDfs(long node)
    {
      visited.set(node, true);
      static if (is(typeof({visitor.n = node;})))
        visitor.n = node;
      static if (is(typeof({visitor.pre;})))
        visitor.pre;
      foreach(w; ne(node))
        if (!visited.at(w))
          {
            static if (is(typeof({visitor.w = w;})))
              visitor.w = w;
            static if (is(typeof(visitor.pren)))
              visitor.pren;
            internalDfs(w);
            static if (is(typeof(visitor.postn)))
              visitor.postn;
          }
      static if (is(typeof(visitor.post)))
        visitor.post;
    }
    internalDfs(startNode);
  }
  void dfs(long startNode)
  {
    struct DefVisitor {}
    dfs!DefVisitor(startNode);
  }
}

DList!string _words;

template removeArray(W, int times)
{
  static if (times == 0)
    alias removeArray = W;
  else static if (times == 1)
    alias removeArray = typeof(function(){W w; return w[0];}());
  else
    {
      static assert(isDynamicArray!W);
      alias removeArray = removeArray!(removeArray!(W, 1), times - 1);
    }
}

template baseType(W)
{
  static if (isDynamicArray!W && !is(W == string))
    alias baseType = baseType!(typeof((delegate() {W w; return w[0];})()));
  else
    alias baseType = W;
}

auto makeSlice(E, W, T...)(W size, T otherSizes)
{
  static if (T.length == 0)
    {
      E[] res;
      res.length = cast(size_t) size;
      return res;
    }
  else
    {
      typeof(makeSlice!E(otherSizes))[] res;
      res.length = cast(size_t) size;
      foreach(ref row; res)
        row = makeSlice!E(otherSizes);
      return res;
    }
}

void read(T...)(ref T t)
{
  void basicTypeRead(W)(ref W w)
  {
    import std.stdio: readln;
    while(_words.empty)
      {
        import std.array: split;
        foreach(word; readln.split)
          {
            _words.insertBack(word);
          }
      }
    import std.conv: to;
    string word = _words.front;
    _words.removeFront;
    w = to!W(word);
  }
  void iterableRead(W)(ref W w)
  {
    foreach(ref element; w)
      read(element);
  }
  void tupleRead(W)(ref W w)
  {
    static foreach(j; 0 .. W.length)
      read(w[j]);
  }
  void structRead(W)(ref W readStruct)
  {
    static foreach(fieldName; FieldNameTuple!W)
      {
        with(readStruct)
          {
            alias fieldSymbol = mixin(W.stringof, ".", fieldName);
            alias typeOfField = typeof(mixin(fieldName));
            static if (hasUDA!(fieldSymbol, If))
              enum condition = getUDAs!(fieldSymbol, If)[0].condition;
            else
              enum condition = "true";

            if (mixin(condition))
              {
                static if (hasUDA!(fieldSymbol, Dim))
                  {
                    static assert(isDynamicArray!(typeOfField)
                                  , text(W.stringof, ".", fieldName, " has Dim UDA but isn't a Dynamic Array."));
                    enum uda = getUDAs!(fieldSymbol, Dim)[0];
                    static assert(getArrayLevel!(typeOfField) == uda.levels,
                                  text(W.stringof, ".", fieldName, " has a Dim UDA with different number of dimensions than it's type."));
                    mixin(fieldName) = mixin(q{makeSlice!(baseType!typeOfField)(}, uda.dimensions, q{)});
                  }
                else static if (isDynamicArray!typeOfField && !is(typeOfField == string))
                  {
                    pragma(msg, "Warning: You probably want to add dimension to input ", W.stringof, ".", fieldName);
                  }
                read(mixin(fieldName));
              }
          }
      }
  }
  static foreach(i; 0 .. T.length)
    {
      static if (isBasicType!(T[i]) || is(T[i] == string))
        basicTypeRead(t[i]);
      else static if (is(typeof({foreach(ref e; t[i]){}})))
        iterableRead(t[i]);
      else static if (isTuple!(T[i]))
        tupleRead(t[i]);
      else static if (isAggregateType!(T[i]))
        structRead(t[i]);
    }
}

auto next(T)()
{
  T t;
  read(t);
  return t;
}

size_t ind(T)(T t)
{
  return cast(size_t)t;
}

ref auto at(R, I)(ref R r, I i)
{
  return r[cast(size_t)i];
}

void set(R, I, V)(ref R r, I i, V v)
{
  r[cast(size_t)i] = v;
}

import std.conv;
import std.traits;
import std.meta;
int _loglevel = -1;
void _log(string functionName, argSeq...)()
{
  foreach(i; 0 .. _loglevel * 4)
    write(' ');
  write(functionName);
  static foreach(arg; argSeq)
    {
      write(" ", arg.stringof, " = ", arg);
    }
  writeln;
}
enum logCall =
  q{
    debug
    {
     {
     _loglevel++;
     alias _parameterTuple = ParameterIdentifierTuple!(mixin(split(__FUNCTION__, ".").back));
     static if (_parameterTuple.length > 0)
       mixin(`_log!(__FUNCTION__, `, [_parameterTuple].joiner(", ").array, `);`);
     else
       _log!(__FUNCTION__);
      }
     foreach(i; 0 .. _loglevel * 4) write(' ');
     writeln('{');
     scope(exit)
       {
         foreach(i; 0 .. _loglevel * 4) write(' ');
         writeln('}');
         _loglevel--;
       }
    }
};

void logSym(S...)(int line = __LINE__, string file = __FUNCTION__)
{
  debug
    {
      foreach(i; 0 .. _loglevel * 4) write(' ');
      write(file, "(", line, "):");
      static foreach(s; S)
        write(" ", s.stringof, " = ", s);
      writeln;

    }
}

Array!E makeArray(E, S)(S size, lazy E value)
{
  auto a = Array!E();
  a.length = cast(size_t) size;
  foreach(ref ai; a)
    ai = value();
  return a;
}
Array!E makeArray(E, S)(S size)
{
  auto a = Array!E();
  a.length = cast(size_t) size;
  return a;
}

template mem(alias F)
{
  ReturnType!F[Tuple!(Parameters!F)] table;
  ReturnType!F mem(Parameters!F args)
  {
    return table.require(tuple(args), F(args));
  }
}

string input(string names, string type = "long")
{
  return text(type, " ", names, "; read(", names, ");");
}

auto pmod(T, W)(T t, W w)
{
  return (t%w + w) % w;
}

void rep(S, F)(F f, S times)
{
  static if (is(typeof(f(i))))
    foreach(i; 0 .. times)
      f(i);
  else
    foreach(i; 0 .. times)
      f();
}

void multi()
{
  foreach(tc; 0 .. next!long)
    next!TestCase.solve(tc);
}

void single()
{
  auto tc = next!TestCase;
  tc.solve;
}

void main()
{
  type;
}

//prewritten code: https://github.com/antma/algo
import std.algorithm;
import std.array;
import std.conv;
import std.math;
import std.range;
import std.stdio;
import std.string;
import std.traits;
import std.container.rbtree;
import std.typecons;

final class InputReader {
  private:
  ubyte[] p, buffer;
  bool eof;
  bool rawRead () {
    if (eof) {
      return false;
    }
    p = stdin.rawRead (buffer);
    if (p.empty) {
      eof = true;
      return false;
    }
    return true;
  }
  ubyte nextByte(bool check) () {
    static if (check) {
      if (p.empty) {
        if (!rawRead ()) {
          return 0;
        }
      }
    }
    auto r = p.front;
    p.popFront ();
    return r;
  }
  public:
  this () {
    buffer = uninitializedArray!(ubyte[])(16<<20);
  }
  bool seekByte (in ubyte lo) {
    while (true) {
      p = p.find! (c => c >= lo);
      if (!p.empty) {
        return false;
      }
      if (!rawRead ()) {
        return true;
      }
    }
  }
  template next(T) if (isSigned!T) {
    T next ()  {
      if (seekByte (45)) {
        return 0;
      }
      T res;
      ubyte b = nextByte!false ();
      if (b == 45) {
        while (true) {
          b = nextByte!true ();
          if (b < 48 || b >= 58) {
            return res;
          }
          res = res * 10 - (b - 48);
        }
      } else {
        res = b - 48;
        while (true) {
          b = nextByte!true ();
          if (b < 48 || b >= 58) {
            return res;
          }
          res = res * 10 + (b - 48);
        }
      }
    }
  }
  template next(T) if (isUnsigned!T) {
    T next () {
      if (seekByte (48)) {
        return 0;
      }
      T res = nextByte!false () - 48;
      while (true) {
        ubyte b = nextByte!true ();
        if (b < 48 || b >= 58) {
          break;
        }
        res = res * 10 + (b - 48);
      }
      return res;
    }
  }
  T[] nextA(T) (in int n) {
    auto a = uninitializedArray!(T[]) (n);
    foreach (i; 0 .. n) {
      a[i] = next!T;
    }
    return a;
  }
}

class G {
  int[][] e;
  int[] d, parent, ss;
  void go (int i) {
    ss[i] = 1;
    foreach (j; e[i]) {
      if (parent[j] == -2) {
        parent[j] = i;
        d[j] = d[i] + 1;
        go (j);
        ss[i] += ss[j];
      }
    }
  }
  this (int n) {
    e = new int[][n];
    d = new int[n];
    parent = new int[n];
    ss = new int[n];
  }
  void addEdge (int i, int j) {
    e[i] ~= j;
    e[j] ~= i;
  }
  void dfs () {
    parent[] = -2;
    parent[0] = -1;
    go (0);
  }
}

alias T = Tuple!(int, int);

alias RBT = RedBlackTree!(T, "a < b", false);

void main() {
  auto r = new InputReader ();
  const n = r.next!uint;
  const k = r.next!uint;
  auto g = new G (n);
  foreach (eid; 1 .. n) {
    const i = r.next!uint - 1;
    const j = r.next!uint - 1;
    g.addEdge (i, j);
  }
  g.dfs ();
  auto x = new int[n];
  foreach (i; 0 .. n) {
    x[i] = (g.ss[i] - 1) - g.d[i];
  }
  sort (x);
  writeln (sum(x[k .. $], 0L));
}

import std.stdio, std.conv, std.functional, std.string;
import std.algorithm, std.array, std.container, std.range, std.typecons;
import std.bigint, std.numeric, std.math, std.random;
import core.bitop;

string FMT_F = "%.10f";

static File _f;
void file_io(string fn) { _f = File(fn, "r"); }
static string[] s_rd;
T _RD(T = long)() { while(!s_rd.length) s_rd = readln.chomp.split; string res = s_rd[0]; s_rd.popFront; return res.to!T; }
T _RD(T = long)(File f) { while(!s_rd.length) s_rd = f.readln.chomp.split; string res = s_rd[0]; s_rd.popFront; return res.to!T; }
T[] _RDA(T = long)(T fix = 0) { auto r = readln.chomp.split.to!(T[]); r[] += fix; return r; }
T[] _RDA(T = long)(File f, T fix = 0) { auto r = f.readln.chomp.split.to!(T[]); r[] += fix; return r; }
T RD(T = long)() { if (_f.isOpen) return _RD!T(_f); else return _RD!T; }
T[] RDA(T = long)(T fix = 0) { if (_f.isOpen)  return _RDA!T(_f, fix); else return _RDA!T(fix); }

size_t[] MAKE_IDX(alias less = "a < b", Range)(Range range) { auto idx = new size_t[](range.length); makeIndex!(less)(range, idx); return idx;}
size_t MIN_POS(alias less = "a < b", Range)(Range range) { auto r = minPos!(less)(range); return range.length - r.length; }

void chmin(T)(ref T x, T y) { x = min(x, y); } void chmax(T)(ref T x, T y) { x = max(x, y); }
bool inside(T)(T x, T b, T e) { return x >= b && x < e; }
T lcm(T)(T x, T y) { return x * (y / gcd(x, y)); }

long mod = 10^^9 + 7;
//long mod = 998_244_353;
//long mod = 1_000_003;
void moda(T)(ref T x, T y) { x = (x + y) % mod; }
void mods(T)(ref T x, T y) { x = ((x + mod) - (y % mod)) % mod; }
void modm(T)(ref T x, T y) { x = (x * y) % mod; }
void modpow(T)(ref T x, T y) { if (!y) { x = 1; return; } auto t = x; x.modpow(y>>1); x.modm(x); if (y&1) x.modm(t); }
void modd(T)(ref T x, T y) { x.modm(y.modpow(mod - 2)); }

void main()
{
	auto n = RD!int;
	auto k = RD!int;
	auto edges = new int[][](n);
	foreach (i; 0..n-1)
	{
		auto u = RD!int-1;
		auto v = RD!int-1;
		edges[u] ~= v;
		edges[v] ~= u;
	}

	auto cnt = new long[](n);

	long dfs(int pos, int par, int depth)
	{
		cnt[pos] += depth;
		long res = 1;
		foreach (to; edges[pos])
		{
			if (to == par) continue;
			res += dfs(to, pos, depth+1);
		}
		cnt[pos] -= res;
		return res;
	}
	dfs(0, -1, 0);

	auto resort = new bool[](n);
	auto index = cnt.MAKE_IDX;
	foreach (i; index[0..n-k])
	{
		resort[i] = true;
	}

	long ans;
	void dfs2(int pos, int par, int depth)
	{
		if (resort[pos])
		{
			foreach (to; edges[pos])
			{
				if (to == par) continue;
				dfs2(to, pos, depth+1);
			}
		}
		else
		{
			ans += depth;
			foreach (to; edges[pos])
			{
				if (to == par) continue;
				dfs2(to, pos, depth);
			}
		}
	}
	dfs2(0, -1, 0);

	writeln(ans);
	stdout.flush;
	debug readln;
}

import std.stdio;
import std.algorithm;
import std.container : DList;

void main()
{
  int n, k;
  stdin.readf!"%d %d\n"(n, k);

  int[][] adj;  adj.length = n+1;
  bool[] visited; visited.length = n+1;
  bool[] tourism; tourism.length = n+1;

  int u, v;
  for (int i=1; i<n; i++) {
    stdin.readf!"%d %d\n"(u, v);
    adj[u] ~= v;
    adj[v] ~= u;
  }

  bool desc(int a, int b) { return adj[a].length > adj[b].length; }
  foreach (a; adj)
    a.sort!desc;

  k = n - k;

  auto q = DList!int(1);
  while (!q.empty() && k > 0) {
    auto city = q.back(); q.removeBack();
    tourism[city] = true;
    k = k - 1;
    if (k == 0) break;

    foreach (neighbor; adj[city])
      if (!visited[neighbor]) {
        visited[neighbor] = true;
        q.insertFront(neighbor);
      }
  }

  int happiness;
  int dfs(int i, int parent) {
    int industrial;

    foreach (child; adj[i])
      if (child == parent)
        continue;
      else
        industrial += dfs(child, i);

    if (tourism[i])
      happiness += industrial;
    else
      industrial += 1;

    return industrial;
  }

  dfs(1, 0);
  writeln(happiness);
}

//prewritten code: https://github.com/antma/algo
import std.algorithm;
import std.array;
import std.conv;
import std.math;
import std.range;
import std.stdio;
import std.string;
import std.traits;

final class Heap(T) {
  private:
    T [] a;
    int [] h;
    int [] g;
    int n;
    int size;
  pure nothrow @nogc
  void heapifyFront (int k) {
    immutable he = h[k];
    int i = k;
    int j = i << 1;
    while (j <= size) {
      if (j < size && a[h[j+1]] < a[h[j]]) {
        j++;
      }
      if (a[h[j]] >= a[he]) {
        break;
      }
      h[i] = h[j];
      g[h[i]] = i;
      i = j;
      j = i << 1;
    }
    if (i != k) {
      h[i] = he;
      g[he] = i;
    }
  }
  pure nothrow @nogc
  void heapifyBack (int k) {
    immutable he = h[k];
    int i = k;
    while (i > 1) {
      int j = i >> 1;
      if (a[he] >= a[h[j]]) {
        break;
      }
      h[i] = h[j];
      g[h[i]] = i;
      i = j;
    }
    if (i != k) {
      h[i] = he;
      g[he] = i;
    }
  }
  pure nothrow @nogc
  void insert (int i) {
    h[++size] = i;
    g[i] = size;
    heapifyBack (size);
  }
  public:
  pure nothrow @nogc
  void decreaseKey (int k, T value) in {
    assert (k >= 0 && k < n);
    assert (value < a[k]);
  } body {
    a[k] = value;
    immutable pos = g[k];
    if (!pos) {
      insert (k);
    } else {
      heapifyBack (pos);
    }
  }
  pure nothrow @nogc
  void update (int k, T value) in {
    assert (k >= 0 && k < n);
  } body {
    immutable pos = g[k];
    if (!pos) {
      a[k] = value;
      insert (k);
    } else if (value < a[k]) {
      a[k] = value;
      heapifyBack (pos);
    } else if (value > a[k]) {
      a[k] = value;
      heapifyFront (pos);
    }
  }
  pure nothrow @nogc
  int extractMin () {
    assert (size > 0);
    immutable he = h[1];
    g[he] = 0;
    if (--size) {
      h[1] = h[size+1];
      g[h[1]] = 1;
      heapifyFront (1);
    }
    return he;
  }
  pure nothrow @nogc
  inout(T) opIndex (size_t index) inout {
    return a[index];
  }

  @property pure nothrow @nogc
  bool empty () const { return size == 0; }

  this (int n_, T default_value = T.init) {
    n = n_;
    size = 0;
    a = uninitializedArray! (T[]) (n);
    a[] = default_value;
    h = new int[n+1];
    g = new int[n];
  }
}

final class InputReader {
  private:
  ubyte[] p, buffer;
  bool eof;
  bool rawRead () {
    if (eof) {
      return false;
    }
    p = stdin.rawRead (buffer);
    if (p.empty) {
      eof = true;
      return false;
    }
    return true;
  }
  ubyte nextByte(bool check) () {
    static if (check) {
      if (p.empty) {
        if (!rawRead ()) {
          return 0;
        }
      }
    }
    auto r = p.front;
    p.popFront ();
    return r;
  }
  public:
  this () {
    buffer = uninitializedArray!(ubyte[])(16<<20);
  }
  bool seekByte (in ubyte lo) {
    while (true) {
      p = p.find! (c => c >= lo);
      if (!p.empty) {
        return false;
      }
      if (!rawRead ()) {
        return true;
      }
    }
  }
  template next(T) if (isSigned!T) {
    T next ()  {
      if (seekByte (45)) {
        return 0;
      }
      T res;
      ubyte b = nextByte!false ();
      if (b == 45) {
        while (true) {
          b = nextByte!true ();
          if (b < 48 || b >= 58) {
            return res;
          }
          res = res * 10 - (b - 48);
        }
      } else {
        res = b - 48;
        while (true) {
          b = nextByte!true ();
          if (b < 48 || b >= 58) {
            return res;
          }
          res = res * 10 + (b - 48);
        }
      }
    }
  }
  template next(T) if (isUnsigned!T) {
    T next () {
      if (seekByte (48)) {
        return 0;
      }
      T res = nextByte!false () - 48;
      while (true) {
        ubyte b = nextByte!true ();
        if (b < 48 || b >= 58) {
          break;
        }
        res = res * 10 + (b - 48);
      }
      return res;
    }
  }
  T[] nextA(T) (in int n) {
    auto a = uninitializedArray!(T[]) (n);
    foreach (i; 0 .. n) {
      a[i] = next!T;
    }
    return a;
  }
}

class G {
  int[][] e;
  int[] d, parent;
  void go (int i) {
    foreach (j; e[i]) {
      if (parent[j] == -2) {
        parent[j] = i;
        d[j] = d[i] + 1;
        go (j);
      }
    }
  }
  this (int n) {
    e = new int[][n];
    d = new int[n];
    parent = new int[n];
  }
  void addEdge (int i, int j) {
    e[i] ~= j;
    e[j] ~= i;
  }
  void dfs () {
    parent[] = -2;
    parent[0] = -1;
    go (0);
  }
}

void main() {
  auto r = new InputReader ();
  const n = r.next!uint;
  const k = r.next!uint;
  auto g = new G (n);
  foreach (eid; 1 .. n) {
    const i = r.next!uint - 1;
    const j = r.next!uint - 1;
    g.addEdge (i, j);
  }
  g.dfs ();
  auto h = new Heap!int (n, int.max / 2);
  long res;
  foreach (i; 0 .. n) {
    h.decreaseKey (i, -g.d[i]);
  }
  foreach (i; 0 .. k) {
    int j = h.extractMin ();
    res -= h[j];
    int o = g.parent[j];
    if (o >= 0) {
      int w = h[o];
      h.update (o, w + 1);
    }
  }
  writeln (res);
}

//prewritten code: https://github.com/antma/algo
import std.algorithm;
import std.array;
import std.conv;
import std.math;
import std.range;
import std.stdio;
import std.string;
import std.traits;
import std.container.rbtree;
import std.typecons;

final class InputReader {
  private:
  ubyte[] p, buffer;
  bool eof;
  bool rawRead () {
    if (eof) {
      return false;
    }
    p = stdin.rawRead (buffer);
    if (p.empty) {
      eof = true;
      return false;
    }
    return true;
  }
  ubyte nextByte(bool check) () {
    static if (check) {
      if (p.empty) {
        if (!rawRead ()) {
          return 0;
        }
      }
    }
    auto r = p.front;
    p.popFront ();
    return r;
  }
  public:
  this () {
    buffer = uninitializedArray!(ubyte[])(16<<20);
  }
  bool seekByte (in ubyte lo) {
    while (true) {
      p = p.find! (c => c >= lo);
      if (!p.empty) {
        return false;
      }
      if (!rawRead ()) {
        return true;
      }
    }
  }
  template next(T) if (isSigned!T) {
    T next ()  {
      if (seekByte (45)) {
        return 0;
      }
      T res;
      ubyte b = nextByte!false ();
      if (b == 45) {
        while (true) {
          b = nextByte!true ();
          if (b < 48 || b >= 58) {
            return res;
          }
          res = res * 10 - (b - 48);
        }
      } else {
        res = b - 48;
        while (true) {
          b = nextByte!true ();
          if (b < 48 || b >= 58) {
            return res;
          }
          res = res * 10 + (b - 48);
        }
      }
    }
  }
  template next(T) if (isUnsigned!T) {
    T next () {
      if (seekByte (48)) {
        return 0;
      }
      T res = nextByte!false () - 48;
      while (true) {
        ubyte b = nextByte!true ();
        if (b < 48 || b >= 58) {
          break;
        }
        res = res * 10 + (b - 48);
      }
      return res;
    }
  }
  T[] nextA(T) (in int n) {
    auto a = uninitializedArray!(T[]) (n);
    foreach (i; 0 .. n) {
      a[i] = next!T;
    }
    return a;
  }
}

class G {
  int[][] e;
  int[] d, parent;
  void go (int i) {
    foreach (j; e[i]) {
      if (parent[j] == -2) {
        parent[j] = i;
        d[j] = d[i] + 1;
        go (j);
      }
    }
  }
  this (int n) {
    e = new int[][n];
    d = new int[n];
    parent = new int[n];
  }
  void addEdge (int i, int j) {
    e[i] ~= j;
    e[j] ~= i;
  }
  void dfs () {
    parent[] = -2;
    parent[0] = -1;
    go (0);
  }
}

alias T = Tuple!(int, int);

alias RBT = RedBlackTree!(T, "a < b", false);

void main() {
  auto r = new InputReader ();
  const n = r.next!uint;
  const k = r.next!uint;
  auto g = new G (n);
  foreach (eid; 1 .. n) {
    const i = r.next!uint - 1;
    const j = r.next!uint - 1;
    g.addEdge (i, j);
  }
  g.dfs ();
  auto t = new RBT();
  foreach (i; 1 .. n) if (g.e[i].length == 1) {
    t.insert (T (g.d[i], i));
  }
  long res;
  auto delta = new int[n];
  foreach (qid; 0 .. k) {
    auto q = t.back;
    debug stderr.writeln (q);
    res += q[0];
    const int j = q[1];
    int o = g.parent[j];
    if (o >= 0) {
      delta[o] = delta[j] + 1;
      t.insert (T (g.d[o] - delta[o], o));
    }
    t.removeBack ();
  }
  writeln (res);
}

//prewritten code: https://github.com/antma/algo
import std.algorithm;
import std.array;
import std.conv;
import std.math;
import std.range;
import std.stdio;
import std.string;
import std.traits;
import std.container.rbtree;
import std.typecons;

final class InputReader {
  private:
  ubyte[] p, buffer;
  bool eof;
  bool rawRead () {
    if (eof) {
      return false;
    }
    p = stdin.rawRead (buffer);
    if (p.empty) {
      eof = true;
      return false;
    }
    return true;
  }
  ubyte nextByte(bool check) () {
    static if (check) {
      if (p.empty) {
        if (!rawRead ()) {
          return 0;
        }
      }
    }
    auto r = p.front;
    p.popFront ();
    return r;
  }
  public:
  this () {
    buffer = uninitializedArray!(ubyte[])(16<<20);
  }
  bool seekByte (in ubyte lo) {
    while (true) {
      p = p.find! (c => c >= lo);
      if (!p.empty) {
        return false;
      }
      if (!rawRead ()) {
        return true;
      }
    }
  }
  template next(T) if (isSigned!T) {
    T next ()  {
      if (seekByte (45)) {
        return 0;
      }
      T res;
      ubyte b = nextByte!false ();
      if (b == 45) {
        while (true) {
          b = nextByte!true ();
          if (b < 48 || b >= 58) {
            return res;
          }
          res = res * 10 - (b - 48);
        }
      } else {
        res = b - 48;
        while (true) {
          b = nextByte!true ();
          if (b < 48 || b >= 58) {
            return res;
          }
          res = res * 10 + (b - 48);
        }
      }
    }
  }
  template next(T) if (isUnsigned!T) {
    T next () {
      if (seekByte (48)) {
        return 0;
      }
      T res = nextByte!false () - 48;
      while (true) {
        ubyte b = nextByte!true ();
        if (b < 48 || b >= 58) {
          break;
        }
        res = res * 10 + (b - 48);
      }
      return res;
    }
  }
  T[] nextA(T) (in int n) {
    auto a = uninitializedArray!(T[]) (n);
    foreach (i; 0 .. n) {
      a[i] = next!T;
    }
    return a;
  }
}

class G {
  int[][] e;
  int[] d, parent;
  void go (int i) {
    foreach (j; e[i]) {
      if (parent[j] == -2) {
        parent[j] = i;
        d[j] = d[i] + 1;
        go (j);
      }
    }
  }
  this (int n) {
    e = new int[][n];
    d = new int[n];
    parent = new int[n];
  }
  void addEdge (int i, int j) {
    e[i] ~= j;
    e[j] ~= i;
  }
  void dfs () {
    parent[] = -2;
    parent[0] = -1;
    go (0);
  }
}

alias T = Tuple!(int, int);

alias RBT = RedBlackTree!(T, "a < b", false);

void main() {
  auto r = new InputReader ();
  const n = r.next!uint;
  const k = r.next!uint;
  auto g = new G (n);
  foreach (eid; 1 .. n) {
    const i = r.next!uint - 1;
    const j = r.next!uint - 1;
    g.addEdge (i, j);
  }
  g.dfs ();
  auto t = new RBT();
  auto intree = new bool[n];
  foreach (i; 1 .. n) if (g.e[i].length == 1) {
    t.insert (T (g.d[i], i));
    intree[i] = true;
  }
  long res;
  auto delta = new int[n];
  foreach (qid; 0 .. k) {
    auto q = t.back;
    debug stderr.writeln (q);
    res += q[0];
    const int j = q[1];
    int o = g.parent[j];
    t.removeBack ();
    if (o > 0) {
      if (intree[o]) {
        t.removeKey (T (g.d[o] - delta[o], o));
      } else intree[o] = true;
      delta[o] += delta[j] + 1;
      t.insert (T (g.d[o] - delta[o], o));
    }
  }
   writeln (res);
}

//prewritten code: https://github.com/antma/algo
import std.algorithm;
import std.array;
import std.conv;
import std.math;
import std.range;
import std.stdio;
import std.string;
import std.traits;
import std.container.rbtree;
import std.typecons;

final class InputReader {
  private:
  ubyte[] p, buffer;
  bool eof;
  bool rawRead () {
    if (eof) {
      return false;
    }
    p = stdin.rawRead (buffer);
    if (p.empty) {
      eof = true;
      return false;
    }
    return true;
  }
  ubyte nextByte(bool check) () {
    static if (check) {
      if (p.empty) {
        if (!rawRead ()) {
          return 0;
        }
      }
    }
    auto r = p.front;
    p.popFront ();
    return r;
  }
  public:
  this () {
    buffer = uninitializedArray!(ubyte[])(16<<20);
  }
  bool seekByte (in ubyte lo) {
    while (true) {
      p = p.find! (c => c >= lo);
      if (!p.empty) {
        return false;
      }
      if (!rawRead ()) {
        return true;
      }
    }
  }
  template next(T) if (isSigned!T) {
    T next ()  {
      if (seekByte (45)) {
        return 0;
      }
      T res;
      ubyte b = nextByte!false ();
      if (b == 45) {
        while (true) {
          b = nextByte!true ();
          if (b < 48 || b >= 58) {
            return res;
          }
          res = res * 10 - (b - 48);
        }
      } else {
        res = b - 48;
        while (true) {
          b = nextByte!true ();
          if (b < 48 || b >= 58) {
            return res;
          }
          res = res * 10 + (b - 48);
        }
      }
    }
  }
  template next(T) if (isUnsigned!T) {
    T next () {
      if (seekByte (48)) {
        return 0;
      }
      T res = nextByte!false () - 48;
      while (true) {
        ubyte b = nextByte!true ();
        if (b < 48 || b >= 58) {
          break;
        }
        res = res * 10 + (b - 48);
      }
      return res;
    }
  }
  T[] nextA(T) (in int n) {
    auto a = uninitializedArray!(T[]) (n);
    foreach (i; 0 .. n) {
      a[i] = next!T;
    }
    return a;
  }
}

class G {
  int[][] e;
  int[] d, parent;
  void go (int i) {
    foreach (j; e[i]) {
      if (parent[j] == -2) {
        parent[j] = i;
        d[j] = d[i] + 1;
        go (j);
      }
    }
  }
  this (int n) {
    e = new int[][n];
    d = new int[n];
    parent = new int[n];
  }
  void addEdge (int i, int j) {
    e[i] ~= j;
    e[j] ~= i;
  }
  void dfs () {
    parent[] = -2;
    parent[0] = -1;
    go (0);
  }
}

alias T = Tuple!(int, int);

alias RBT = RedBlackTree!(T, "a < b", false);

void main() {
  auto r = new InputReader ();
  const n = r.next!uint;
  const k = r.next!uint;
  auto g = new G (n);
  foreach (eid; 1 .. n) {
    const i = r.next!uint - 1;
    const j = r.next!uint - 1;
    g.addEdge (i, j);
  }
  g.dfs ();
  auto t = new RBT();
  foreach (i; 1 .. n) if (g.e[i].length == 1) {
    t.insert (T (g.d[i], i));
  }
  long res;
  auto delta = new int[n];
  foreach (qid; 0 .. k) {
    auto q = t.back;
    debug stderr.writeln (q);
    res += q[0];
    const int j = q[1];
    int o = g.parent[j];
    if (o > 0) {
      delta[o] = delta[j] + 1;
      t.insert (T (g.d[o] - delta[o], o));
    }
    t.removeBack ();
  }
  writeln (res);
}


The Little Elephant loves Ukraine very much. Most of all he loves town Rozdol (ukr. "Rozdil").However, Rozdil is dangerous to settle, so the Little Elephant wants to go to some other town. The Little Elephant doesn't like to spend much time on travelling, so for his journey he will choose a town that needs minimum time to travel to. If there are multiple such cities, then the Little Elephant won't go anywhere.For each town except for Rozdil you know the time needed to travel to this town. Find the town the Little Elephant will go to or print "Still Rozdil", if he stays in Rozdil.

The first line contains a single integer n (1 ≤ n ≤ 105) — the number of cities. The next line contains n integers, separated by single spaces: the i-th integer represents the time needed to go from town Rozdil to the i-th town. The time values are positive integers, not exceeding 109. You can consider the cities numbered from 1 to n, inclusive. Rozdil is not among the numbered cities.

Print the answer on a single line — the number of the town the Little Elephant will go to. If there are multiple cities with minimum travel time, print "Still Rozdil" (without the quotes).

NoteIn the first sample there are only two cities where the Little Elephant can go. The travel time for the first town equals 7, to the second one — 4. The town which is closest to Rodzil (the only one) is the second one, so the answer is 2.In the second sample the closest cities are cities two and five, the travelling time to both of them equals 4, so the answer is "Still Rozdil".

import std.stdio, std.algorithm;

void main() {
    uint n;

    readf("%s\n", &n);

    ulong[2][] arr = new ulong[2][n];

    for(uint i; i < n; ++i) {
        readf("%s ", &arr[i][1]); arr[i][0] = i;
    }

    arr.sort!((ref a, ref b) => a[1] < b[1]);

    if(arr[0][1] == arr[1][1]) {
        writeln("Still Rozdil");
    }
    else {
        writeln(arr[0][0]+1);
    }
}

import std.stdio, std.algorithm;

void main() {
    uint n;

    readf("%s\n", &n);

    ulong[] arr = new ulong[n];

    for(uint i; i < n; ++i) {
        readf("%s ", &arr[i]);
    }

    //sort!((ulong a, ulong b) => a < b)(arr);
    sort!((a, b) => a < b)(arr);

    if(arr[0] == arr[1]) {
        writeln("Still Rozdil");
    }
    else {
        writeln(arr[0]);
    }
}


Madoka finally found the administrator password for her computer. Her father is a well-known popularizer of mathematics, so the password is the answer to the following problem.Find the maximum decimal number without zeroes and with no equal digits in a row, such that the sum of its digits is $$$n$$$.Madoka is too tired of math to solve it herself, so help her to solve this problem!

Each test contains multiple test cases. The first line contains a single integer $$$t$$$ ($$$1 \le t \le 1000$$$) — the number of test cases. Description of the test cases follows. The only line of each test case contains an integer $$$n$$$ ($$$1 \le n \le 1000$$$) — the required sum of the digits.

For each test case print the maximum number you can obtain.

NoteThe only numbers with the sum of digits equal to $$$2$$$ without zeros are $$$2$$$ and $$$11$$$. But the last one has two ones in a row, so it's not valid. That's why the answer is $$$2$$$.The only numbers with the sum of digits equal to $$$3$$$ without zeros are $$$111$$$, $$$12$$$, $$$21$$$, and $$$3$$$. The first one has $$$2$$$ ones in a row, so it's not valid. So the maximum valid number is $$$21$$$.The only numbers with the sum of digits equals to $$$4$$$ without zeros are $$$1111$$$, $$$211$$$, $$$121$$$, $$$112$$$, $$$13$$$, $$$31$$$, $$$22$$$, and $$$4$$$. Numbers $$$1111$$$, $$$211$$$, $$$112$$$, $$$22$$$ aren't valid, because they have some identical digits in a row. So the maximum valid number is $$$121$$$.

import std;
void main () {
	foreach (t; 0..readln.strip.to!int) {
		auto n = readln.strip.to!int;
		"21".cycle.drop (n % 3 == 1).take ((n * 2 + 1) / 3).writeln;
	}
}

import std.algorithm;
import std.conv;
import std.range;
import std.stdio;
import std.string;

void main ()
{
	auto tests = readln.strip.to !(int);
	foreach (test; 0..tests)
	{
		auto n = readln.strip.to !(int);
		writeln ("21".cycle.drop (n % 3 == 1).take ((n * 2 + 1) / 3));
	}
}


You are an upcoming movie director, and you have just released your first movie. You have also launched a simple review site with two buttons to press — upvote and downvote.However, the site is not so simple on the inside. There are two servers, each with its separate counts for the upvotes and the downvotes.$$$n$$$ reviewers enter the site one by one. Each reviewer is one of the following types:   type $$$1$$$: a reviewer has watched the movie, and they like it — they press the upvote button;  type $$$2$$$: a reviewer has watched the movie, and they dislike it — they press the downvote button;  type $$$3$$$: a reviewer hasn't watched the movie — they look at the current number of upvotes and downvotes of the movie on the server they are in and decide what button to press. If there are more downvotes than upvotes, then a reviewer downvotes the movie. Otherwise, they upvote the movie. Each reviewer votes on the movie exactly once.Since you have two servers, you can actually manipulate the votes so that your movie gets as many upvotes as possible. When a reviewer enters a site, you know their type, and you can send them either to the first server or to the second one.What is the maximum total number of upvotes you can gather over both servers if you decide which server to send each reviewer to?

The first line contains a single integer $$$t$$$ ($$$1 \le t \le 10^4$$$) — the number of testcases. Then the descriptions of $$$t$$$ testcases follow. The first line of each testcase contains a single integer $$$n$$$ ($$$1 \le n \le 50$$$) — the number of reviewers. The second line of each testcase contains $$$n$$$ integers $$$r_1, r_2, \dots, r_n$$$ ($$$1 \le r_i \le 3$$$) — the types of the reviewers in the same order they enter the site.

For each testcase print a single integer — the maximum total number of upvotes you can gather over both servers if you decide which server to send each reviewer to.

NoteIn the first testcase of the example you can send the only reviewer to either of the servers — they'll downvote anyway. The movie won't receive any upvotes.In the second testcase of the example you can send all reviewers to the first server:   the first reviewer upvotes;  the second reviewer downvotes;  the last reviewer sees that the number of downvotes is not greater than the number of upvotes — upvote themselves. There are two upvotes in total. Alternatevely, you can send the first and the second reviewers to the first server and the last reviewer — to the second server:   the first reviewer upvotes on the first server;  the second reviewer downvotes on the first server;  the last reviewer sees no upvotes or downvotes on the second server — upvote themselves.

import std.stdio, std.string, std.algorithm, std.range;
void main()
{
    int q;
    readf!"%d\n"(q);
    foreach (_; 0 .. q)
    {
        readln();
        writeln(readln.split.filter!(a => a != "2").array.length);
    }
}

import std.stdio, std.conv, std.functional, std.string;
import std.algorithm, std.array, std.container, std.range, std.typecons;
import std.bigint, std.numeric, std.math, std.random;
import core.bitop;

string FMT_F = "%.10f";

static File _f;
void file_io(string fn) { _f = File(fn, "r"); }
static string[] s_rd;
T _RD(T = long)() { while(!s_rd.length) s_rd = readln.chomp.split; string res = s_rd[0]; s_rd.popFront; return res.to!T; }
T _RD(T = long)(File f) { while(!s_rd.length) s_rd = f.readln.chomp.split; string res = s_rd[0]; s_rd.popFront; return res.to!T; }
T[] _RDA(T = long)(T fix = 0) { auto r = readln.chomp.split.to!(T[]); r[] += fix; return r; }
T[] _RDA(T = long)(File f, T fix = 0) { auto r = f.readln.chomp.split.to!(T[]); r[] += fix; return r; }
T RD(T = long)() { if (_f.isOpen) return _RD!T(_f); else return _RD!T; }
T[] RDA(T = long)(T fix = 0) { if (_f.isOpen)  return _RDA!T(_f, fix); else return _RDA!T(fix); }

size_t[] MAKE_IDX(alias less = "a < b", Range)(Range range) { auto idx = new size_t[](range.length); makeIndex!(less)(range, idx); return idx;}
size_t MIN_POS(alias less = "a < b", Range)(Range range) { auto r = minPos!(less)(range); return range.length - r.length; }

void chmin(T)(ref T x, T y) { x = min(x, y); } void chmax(T)(ref T x, T y) { x = max(x, y); }
bool inside(T)(T x, T b, T e) { return x >= b && x < e; }
T lcm(T)(T x, T y) { return x * (y / gcd(x, y)); }

long mod = 10^^9 + 7;
//long mod = 998_244_353;
//long mod = 1_000_003;
void moda(ref long x, long y) { x = (x + y) % mod; }
void mods(ref long x, long y) { x = ((x + mod) - (y % mod)) % mod; }
void modm(ref long x, long y) { x = (x * y) % mod; }
void modpow(ref long x, long y) { if (!y) { x = 1; return; } auto t = x; x.modpow(y>>1); x.modm(x); if (y&1) x.modm(t); }
void modd(ref long x, long y) { y.modpow(mod - 2); x.modm(y); }

void main()
{
	auto t = RD!int;
	auto ans = new long[](t);
	foreach (ti; 0..t)
	{
		auto n = RD!int;
		auto r = RDA;
		foreach (i; 0..n)
		{
			if (r[i] == 2) continue;
			++ans[ti];
		}
	}

	foreach (e; ans)
		writeln(e);
	stdout.flush;
	debug readln;
}


$$$n$$$ robots have escaped from your laboratory! You have to find them as soon as possible, because these robots are experimental, and their behavior is not tested yet, so they may be really dangerous!Fortunately, even though your robots have escaped, you still have some control over them. First of all, you know the location of each robot: the world you live in can be modeled as an infinite coordinate plane, and the $$$i$$$-th robot is currently located at the point having coordinates ($$$x_i$$$, $$$y_i$$$). Furthermore, you may send exactly one command to all of the robots. The command should contain two integer numbers $$$X$$$ and $$$Y$$$, and when each robot receives this command, it starts moving towards the point having coordinates ($$$X$$$, $$$Y$$$). The robot stops its movement in two cases:  either it reaches ($$$X$$$, $$$Y$$$);  or it cannot get any closer to ($$$X$$$, $$$Y$$$). Normally, all robots should be able to get from any point of the coordinate plane to any other point. Each robot usually can perform four actions to move. Let's denote the current coordinates of the robot as ($$$x_c$$$, $$$y_c$$$). Then the movement system allows it to move to any of the four adjacent points:  the first action allows it to move from ($$$x_c$$$, $$$y_c$$$) to ($$$x_c - 1$$$, $$$y_c$$$);  the second action allows it to move from ($$$x_c$$$, $$$y_c$$$) to ($$$x_c$$$, $$$y_c + 1$$$);  the third action allows it to move from ($$$x_c$$$, $$$y_c$$$) to ($$$x_c + 1$$$, $$$y_c$$$);  the fourth action allows it to move from ($$$x_c$$$, $$$y_c$$$) to ($$$x_c$$$, $$$y_c - 1$$$). Unfortunately, it seems that some movement systems of some robots are malfunctioning. For each robot you know which actions it can perform, and which it cannot perform.You want to send a command so all robots gather at the same point. To do so, you have to choose a pair of integer numbers $$$X$$$ and $$$Y$$$ so that each robot can reach the point ($$$X$$$, $$$Y$$$). Is it possible to find such a point?

The first line contains one integer $$$q$$$ ($$$1 \le q \le 10^5$$$) — the number of queries. Then $$$q$$$ queries follow. Each query begins with one line containing one integer $$$n$$$ ($$$1 \le n \le 10^5$$$) — the number of robots in the query. Then $$$n$$$ lines follow, the $$$i$$$-th of these lines describes the $$$i$$$-th robot in the current query: it contains six integer numbers $$$x_i$$$, $$$y_i$$$, $$$f_{i, 1}$$$, $$$f_{i, 2}$$$, $$$f_{i, 3}$$$ and $$$f_{i, 4}$$$ ($$$-10^5 \le x_i, y_i \le 10^5$$$, $$$0 \le f_{i, j} \le 1$$$). The first two numbers describe the initial location of the $$$i$$$-th robot, and the following four numbers describe which actions the $$$i$$$-th robot can use to move ($$$f_{i, j} = 1$$$ if the $$$i$$$-th robot can use the $$$j$$$-th action, and $$$f_{i, j} = 0$$$ if it cannot use the $$$j$$$-th action). It is guaranteed that the total number of robots over all queries does not exceed $$$10^5$$$.

You should answer each query independently, in the order these queries appear in the input. To answer a query, you should do one of the following:   if it is impossible to find a point that is reachable by all $$$n$$$ robots, print one number $$$0$$$ on a separate line;  if it is possible to find a point that is reachable by all $$$n$$$ robots, print three space-separated integers on the same line: $$$1$$$ $$$X$$$ $$$Y$$$, where $$$X$$$ and $$$Y$$$ are the coordinates of the point reachable by all $$$n$$$ robots. Both $$$X$$$ and $$$Y$$$ should not exceed $$$10^5$$$ by absolute value; it is guaranteed that if there exists at least one point reachable by all robots, then at least one of such points has both coordinates not exceeding $$$10^5$$$ by absolute value.

import std.stdio;
import std.algorithm;

struct Point {
    int x;
    int y;
}

struct Action {
    bool up;
    bool down;
    bool left;
    bool right;
}

struct Box {
    int top;
    int bottom;
    int left;
    int right;

    bool valid() {
        return top >= bottom && left <= right;
    }
}

void solve() {
    int n;
    readf(" %s", n);

    auto p = new Point[n];
    auto a = new Action[n];
    foreach(i; 0..n) {
        readf(" %s %s", p[i].x, p[i].y);
        readf(" %b %b %b %b", a[i].left, a[i].up, a[i].right, a[i].down);
    }

    auto box = Box();
    box.top = int.max;
    box.bottom = int.min;
    box.left = int.min;
    box.right = int.max;
    auto inf = box;

    foreach(i; 0..n) {
        if (!a[i].up) {
            box.top = min(box.top, p[i].y);
        }
        if (!a[i].down) {
            box.bottom = max(box.bottom, p[i].y);
        }
        if (!a[i].left) {
            box.left = max(box.left, p[i].x);
        }
        if (!a[i].right) {
            box.right = min(box.right, p[i].x);
        }
        if (!box.valid()) {
            writeln(0);
            return;
        }
    }
    int x;
    if (box.left != inf.left) {
        x = box.left;
    } else if (box.right != inf.right) {
        x = box.right;
    } else {
        x = 0;
    }

    int y;
    if (box.top != inf.top) {
        y = box.top;
    } else if (box.bottom != inf.bottom){
        y = box.bottom;
    } else {
        y = 0;
    }
    writeln(1, " ", x, " ", y);
}

void main() {
    int q;
    readf(" %s", q);

    foreach(i; 0..q) {
        solve();
    }
}

import std.stdio;
import std.algorithm;

void solve() {
    int n;
    readf(" %s", n);

    int A, B, C, D;
    A = D = -100000;
    B = C =  100000;
    foreach(i; 0..n) {
        int x, y;
        bool a, b, c, d;
        readf(" %s %s %b %b %b %b", x, y, a, b, c, d);
        // left, up, right, down
        if (!a) A = max(A, x);
        if (!b) B = min(B, y);
        if (!c) C = min(C, x);
        if (!d) D = max(D, y);
    }
    if (!(A <= C && D <= B)) writeln(0); else writeln(1, " ", (A+C)/2, " ", (B+D)/2);
}

void main() {
    int q;
    readf(" %s", q);

    foreach(i; 0..q) {
        solve();
    }
}

import std.stdio;
import std.algorithm;

void main(){
	const int LOWER = -100000, HIGHER = 100000;
	int q;
	readf(" %s", &q);

	for(int i = 0; i < q; i++){
		int n = 0;
		readf(" %s", &n);

		int leftBound = LOWER;
		int rightBound = HIGHER;
		int bottomBound = LOWER;
		int topBound = HIGHER;

		for(int j = 0; j < n; j++){
			int x = 0, y = 0;
			readf(" %s %s", &x, &y);

			int downI = 0, upI = 0, rightI = 0, leftI = 0;
			readf(" %s %s %s %s", &leftI, &upI, &rightI, &downI);
			if(downI == 0){
				bottomBound = max(bottomBound, y);
			}
			if(upI == 0){
				topBound = min(topBound, y);
			}
			if(leftI == 0){
				leftBound = max(leftBound, x);
			}
			if(rightI == 0){
				rightBound = min(rightBound, x);
			}
		}
		if(rightBound < leftBound || topBound < bottomBound){
			writef("0\n");
		}else{
			writef("1 %d %d\n", leftBound, bottomBound);
		}
	}

}

import std.stdio, std.conv, std.functional, std.string;
import std.algorithm, std.array, std.container, std.range, std.typecons;
import std.numeric, std.math, std.random;
import core.bitop;

string FMT_F = "%.10f";

static string[] s_rd;
T RD(T = long)() { while(!s_rd.length) s_rd = readln.chomp.split; string res = s_rd[0]; s_rd.popFront; return res.to!T; }
string RDR()() { return readln.chomp; }
T[] ARR(T = long)(in string str, T fix = 0) { auto r = str.split.to!(T[]); r[] += fix; return r; }
T[] RDA(T = long)(T fix = 0) { auto r = readln.chomp.split.to!(T[]); r[] += fix; return r; }
T[][] RDA2(T = long)(size_t n, T[] fix = []) { auto r = new T[][](n); foreach (i; 0..n) { r[i] = readln.chomp.split.to!(T[]); foreach (j, e; fix) r[i][j] += e; } return r; }
size_t[] MAKE_IDX(alias less = "a < b", Range)(Range range) { auto idx = new size_t[](range.length); makeIndex!(less)(range, idx); return idx;}
size_t MIN_POS(alias less = "a < b", Range)(Range range) { auto r = minPos!(less)(range); return range.length - r.length; }

bool inside(T)(T x, T b, T e) { return x >= b && x < e; }
long lcm(long x, long y) { return x * y / gcd(x, y); }

//long mod = 10^^9 + 7;
long mod = 998_244_353;
//long mod = 1_000_003;
void moda(ref long x, long y) { x = (x + y) % mod; }
void mods(ref long x, long y) { x = ((x + mod) - (y % mod)) % mod; }
void modm(ref long x, long y) { x = (x * y) % mod; }

void main()
{
	auto q = RD!int;
	auto ans = new long[][](q);
	foreach (i; 0..q)
	{
		auto n = RD!int;
		long l = -(10^^5), t = -(10^^5), r = 10^^5, b = 10^^5;
		foreach (j; 0..n)
		{
			auto a = RDA;
			if (a[2] == 0)
				l = max(l, a[0]);
			if (a[3] == 0)
				b = min(b, a[1]);
			if (a[4] == 0)
				r = min(r, a[0]);
			if (a[5] == 0)
				t = max(t, a[1]);
		}
		if (l > r || t > b)
		{
			ans[i] = [0];
		}
		else
		{
			ans[i] = [1, l, t];
		}
	}

	foreach (e; ans)
	{
		e.map!(to!string).join(" ").writeln;
	}
	stdout.flush();
	debug readln();
}

import std.stdio;
import std.algorithm;

void main(){
	const int LOWER = -100000, HIGHER = 100000;
	int q;
	readf(" %s", &q);

	for(int i = 0; i < q; i++){
		int n = 0;
		readf(" %s", &n);

		int leftBound = LOWER;
		int rightBound = HIGHER;
		int bottomBound = LOWER;
		int topBound = HIGHER;

		for(int j = 0; j < n; j++){
			int x = 0, y = 0;
			readf(" %s %s", &x, &y);

			int downI = 0, upI = 0, rightI = 0, leftI = 0;
			readf(" %s %s %s %s", &downI, &upI, &rightI, &leftI);
			if(downI == 0){
				bottomBound = max(bottomBound, y);
			}
			if(upI == 0){
				topBound = min(topBound, y);
			}
			if(leftI == 0){
				leftBound = max(leftBound, x);
			}
			if(rightI == 0){
				rightBound = min(rightBound, x);
			}

			if(rightBound < leftBound || topBound < bottomBound){
				write("0\n");
			}else{
				write("1 %d, %d\n", leftBound, bottomBound);
			}
		}
	}

}

import std.stdio;
import std.algorithm;

void main(){
	const int LOWER = -100000, HIGHER = 100000;
	int q;
	readf(" %s", &q);

	for(int i = 0; i < q; i++){
		int n = 0;
		readf(" %s", &n);

		int leftBound = LOWER;
		int rightBound = HIGHER;
		int bottomBound = LOWER;
		int topBound = HIGHER;

		for(int j = 0; j < n; j++){
			int x = 0, y = 0;
			readf(" %s %s", &x, &y);

			int downI = 0, upI = 0, rightI = 0, leftI = 0;
			readf(" %s %s %s %s", &downI, &upI, &rightI, &leftI);
			if(downI == 0){
				bottomBound = max(bottomBound, y);
			}
			if(upI == 0){
				topBound = min(topBound, y);
			}
			if(leftI == 0){
				leftBound = max(leftBound, x);
			}
			if(rightI == 0){
				rightBound = min(rightBound, x);
			}
		}
		if(rightBound < leftBound || topBound < bottomBound){
			writef("0\n");
		}else{
			writef("1 %d %d\n", leftBound, bottomBound);
		}
	}

}


In this problem you have to implement an algorithm to defragment your hard disk. The hard disk consists of a sequence of clusters, numbered by integers from 1 to n. The disk has m recorded files, the i-th file occupies clusters with numbers ai, 1, ai, 2, ..., ai, ni. These clusters are not necessarily located consecutively on the disk, but the order in which they are given corresponds to their sequence in the file (cluster ai, 1 contains the first fragment of the i-th file, cluster ai, 2 has the second fragment, etc.). Also the disc must have one or several clusters which are free from files.You are permitted to perform operations of copying the contents of cluster number i to cluster number j (i and j must be different). Moreover, if the cluster number j used to keep some information, it is lost forever. Clusters are not cleaned, but after the defragmentation is complete, some of them are simply declared unusable (although they may possibly still contain some fragments of files).Your task is to use a sequence of copy operations to ensure that each file occupies a contiguous area of memory. Each file should occupy a consecutive cluster section, the files must follow one after another from the beginning of the hard disk. After defragmentation all free (unused) clusters should be at the end of the hard disk. After defragmenting files can be placed in an arbitrary order. Clusters of each file should go consecutively from first to last. See explanatory examples in the notes.Print the sequence of operations leading to the disk defragmentation. Note that you do not have to minimize the number of operations, but it should not exceed 2n.

The first line contains two integers n and m (1 ≤ n, m ≤ 200) — the number of clusters and the number of files, correspondingly. Next m lines contain descriptions of the files. The first number in the line is ni (ni ≥ 1), the number of clusters occupied by the i-th file. Then follow ni numbers ai, 1, ai, 2, ..., ai, ni (1 ≤ ai, j ≤ n). It is guaranteed that each cluster number occurs not more than once and , that is, there exists at least one unused cluster. Numbers on each line are separated by spaces.

In the first line print a single integer k (0 ≤ k ≤ 2n) — the number of operations needed to defragment the disk. Next k lines should contain the operations' descriptions as "i j" (copy the contents of the cluster number i to the cluster number j).

NoteLet's say that a disk consists of 8 clusters and contains two files. The first file occupies two clusters and the second file occupies three clusters. Let's look at examples of correct and incorrect positions of files after defragmentation. Example 2: each file must occupy a contiguous area of memory.Example 3: the order of files to each other is not important, at first the second file can be written, and then — the first one.Example 4: violating the order of file fragments to each other is not allowed.Example 5: unused clusters should be located at the end, and in this example the unused clusters are 3, 7, 8.

import core.bitop, std.bitmanip;
import core.checkedint;
import std.algorithm, std.functional;
import std.array, std.container;
import std.bigint;
import std.conv;
import std.math, std.numeric;
import std.range, std.range.interfaces;
import std.stdio, std.string;
import std.typecons;

void main()
{

    int n, m;
    readf("%s %s", &n, &m);
    readln;

    auto idx = new Tuple!(int, int)[] (n+1);
    idx[] = tuple(-1, -1);
    auto arr = new int[][] (m);
    foreach (i; 0 .. m) {
        auto inp = readln.chomp.split.dropOne.map!(to!int).array;
        foreach (j, e; inp) {
           arr[i] ~= e;
           idx[e] = tuple(i, j.to!int);
        }
    }

    debug { idx.writeln; }

    Tuple!(int, int)[] ans;

    void mv(int src, int dst) {
        debug { writeln(src, ' ', dst); }

        auto sidx = idx[src];
        arr[sidx[0]][sidx[1]] = dst;
        idx[dst] = sidx;
        idx[src] = tuple(-1, -1);

        ans ~= tuple(src, dst);
    }

    int freePos = 1;
    while (idx[freePos] != tuple(-1, -1)) { ++freePos; }

    int p = 1;
    foreach (i; 0 .. m) {
        foreach (j, e; arr[i]) {
            if (p != arr[i][j]) {
                if (idx[p] != tuple(-1, -1)) { mv(p, freePos); }
                freePos = arr[i][j];
                mv(arr[i][j], p);
            }
            ++p;
        }
    }

    ans.length.writeln;
    ans.each!(t => writeln(t[0], ' ', t[1]));
}

import core.bitop, std.bitmanip;
import core.checkedint;
import std.algorithm, std.functional;
import std.array, std.container;
import std.bigint;
import std.conv;
import std.math, std.numeric;
import std.range, std.range.interfaces;
import std.stdio, std.string;
import std.typecons;

void main()
{

    int n, m;
    readf("%s %s", &n, &m);
    readln;

    auto place = new int[] (n+1);
    place[] = -1;
    RedBlackTree!int[] arr;
    foreach (i; 0 .. m) {
        auto a = readln.chomp.split.dropOne.map!(to!int).array;
        arr ~= make!(RedBlackTree!int)(a);
        foreach (e; a) { place[e] = i; }
    }

    int fre = 1;
    while (place[fre] != -1) { ++fre; }

    auto tot = arr.map!(t => t.length).sum;
    Tuple!(int, int)[] ans;

    void mv(int src, ref int dst) {
        arr[place[src]].removeKey(src);
        arr[place[src]].insert(dst);
        place[dst] = place[src];
        place[src] = -1;
        ans ~= tuple(src, dst);
        dst = src;
    }

    int aidx = 0;
    foreach (p; 1 .. tot+1) {
        if (arr[aidx].empty()) { ++aidx; }

        if (place[p] != aidx) {
            if (p != fre) {
                mv(p.to!int, fre);
            }

            mv(arr[aidx].front, fre);
        }

        arr[aidx].removeFront();
    }

    ans.length.writeln;
    ans.each!(t => writeln(t[0], ' ', t[1]));
}

import core.bitop, std.bitmanip;
import core.checkedint;
import std.algorithm, std.functional;
import std.array, std.container;
import std.bigint;
import std.conv;
import std.math, std.numeric;
import std.range, std.range.interfaces;
import std.stdio, std.string;
import std.typecons;

void main()
{

    int n, m;
    readf("%s %s", &n, &m);
    readln;

    auto place = new int[] (n+1);
    place[] = -1;
    RedBlackTree!int[] arr;
    foreach (i; 0 .. m) {
        auto a = readln.chomp.split.dropOne.map!(to!int).array;
        arr ~= make!(RedBlackTree!int)(a);
        foreach (e; a) { place[e] = i; }
    }

    int fre = 1;
    while (place[fre] != -1) { ++fre; }

    auto tot = arr.map!(t => t.length).sum;
    Tuple!(int, int)[] ans;

    void mv(int src, ref int dst) {
        arr[place[src]].removeKey(src);
        arr[place[src]].insert(dst);
        place[dst] = place[src];
        place[src] = -1;
        ans ~= tuple(src, dst);
        dst = src;
    }

    int aidx = 0;
    foreach (p; 1 .. tot+1) {
        if (arr[aidx].empty()) { ++aidx; }

        if (p != fre) {
            mv(p.to!int, fre);
        }

        mv(arr[aidx].front, fre);

        arr[aidx].removeFront();
    }

    ans.length.writeln;
    ans.each!(t => writeln(t[0], ' ', t[1]));
}


You are given an array $$$a$$$ of $$$n$$$ positive integers numbered from $$$1$$$ to $$$n$$$. Let's call an array integral if for any two, not necessarily different, numbers $$$x$$$ and $$$y$$$ from this array, $$$x \ge y$$$, the number $$$\left \lfloor \frac{x}{y} \right \rfloor$$$ ($$$x$$$ divided by $$$y$$$ with rounding down) is also in this array.You are guaranteed that all numbers in $$$a$$$ do not exceed $$$c$$$. Your task is to check whether this array is integral.

The input consists of multiple test cases. The first line contains a single integer $$$t$$$ ($$$1 \le t \le 10^4$$$) — the number of test cases. Description of the test cases follows. The first line of each test case contains two integers $$$n$$$ and $$$c$$$ ($$$1 \le n \le 10^6$$$, $$$1 \le c \le 10^6$$$) — the size of $$$a$$$ and the limit for the numbers in the array. The second line of each test case contains $$$n$$$ integers $$$a_1$$$, $$$a_2$$$, ..., $$$a_n$$$ ($$$1 \le a_i \le c$$$) — the array $$$a$$$. Let $$$N$$$ be the sum of $$$n$$$ over all test cases and $$$C$$$ be the sum of $$$c$$$ over all test cases. It is guaranteed that $$$N \le 10^6$$$ and $$$C \le 10^6$$$.

For each test case print Yes if the array is integral and No otherwise.

NoteIn the first test case it is easy to see that the array is integral:   $$$\left \lfloor \frac{1}{1} \right \rfloor = 1$$$, $$$a_1 = 1$$$, this number occurs in the arry  $$$\left \lfloor \frac{2}{2} \right \rfloor = 1$$$  $$$\left \lfloor \frac{5}{5} \right \rfloor = 1$$$  $$$\left \lfloor \frac{2}{1} \right \rfloor = 2$$$, $$$a_2 = 2$$$, this number occurs in the array  $$$\left \lfloor \frac{5}{1} \right \rfloor = 5$$$, $$$a_3 = 5$$$, this number occurs in the array  $$$\left \lfloor \frac{5}{2} \right \rfloor = 2$$$, $$$a_2 = 2$$$, this number occurs in the array Thus, the condition is met and the array is integral.In the second test case it is enough to see that$$$\left \lfloor \frac{7}{3} \right \rfloor = \left \lfloor 2\frac{1}{3} \right \rfloor = 2$$$, this number is not in $$$a$$$, that's why it is not integral.In the third test case $$$\left \lfloor \frac{2}{2} \right \rfloor = 1$$$, but there is only $$$2$$$ in the array, that's why it is not integral.

import std;

const int N = 1_000_101;

int n, c;
int[N] a, ex, s;

int read() {
    int x = 0, f = 1;
    auto ch = getchar();
    while(ch > '9' || ch < '0') { if(ch == '-') f = -1; ch = getchar(); }
    while(ch >= '0' && ch <= '9') x = x * 10 + ch - 48, ch = getchar();
    return x * f;
}

void main()
{
    int t;
    scanf("%d", &t);
    getchar();
    outer: foreach(_; 0..t)
    {
        scanf("%d %d\n", &n, &c);
        for(int i = 1;i <= c;i++) ex[i] = false;
        for(int i = 1;i <= n;i++) a[i] = read(), ex[a[i]] = true;
        for(int i = 1;i <= c;i++) s[i] = s[i - 1] + ex[i];
        for(int k = 1;k <= c;k++) if(!ex[k]) {
        for(int y = 1;k * y <= c;y++) if(ex[y]) {
            int l = k * y, r = min(c,(k + 1) * y - 1);
                if(s[r] - s[l - 1]) {
                    printf("No\n");
                    continue outer;
                }
            }
        }
        printf("Yes\n");
    }
}

import std;

const int N = 1_000_101;

int n, c;
int[N] a, ex, s;

void main()
{
    int t;
    scanf("%d", &t);
    getchar();
    outer: foreach(_; 0..t)
    {
        scanf("%d %d\n", &n, &c);
        for(int i = 1;i <= c;i++) ex[i] = false;
        auto tmp = readln.split.to!(int[]);
        for(int i = 1;i <= n;i++) a[i] = tmp[i - 1], ex[a[i]] = true;
        for(int i = 1;i <= c;i++) s[i] = s[i - 1] + ex[i];
        for(int k = 1;k <= c;k++) if(!ex[k]) {
        for(int y = 1;k * y <= c;y++) if(ex[y]) {
            int l = k * y, r = min(c,(k + 1) * y - 1);
                if(s[r] - s[l - 1]) {
                    printf("No\n");
                    continue outer;
                }
            }
        }
        printf("Yes\n");
    }
}

import std.stdio;
import std.math;
import std.numeric;
import std.container;
import std.typecons;
import core.stdc.stdio : scanf;
import std.conv;
import std.array;
import std.string;
import std.range;
import std.algorithm;

T read(T)() { return readln.chomp.to!T; }
T[] readarray(T)() { return readln.chomp.split(" ").map!(to!T).array; }

struct BIT(Num, Num zero) {
    int N;
    Num[] dat; // dat is 1-indexed
    this(int N) {
        this.N = N;
        dat = new Num[N + 1];
        dat[] = zero;
    }
    // add x to i-th (0-indexed) element
    void add(int i, Num x) {
        i++; // make 1-indexed
        while (i <= N) {
            dat[i] += x;
            i += i & -i;
        }
    }
    void add(long i, Num x) { add(cast(int)i, x); }
    // return the sum of [0, i) (0-indexed) element
    Num query(int i) {
        Num s = zero;
        while (i > 0) {
            s += dat[i];
            i -= i & -i;
        }
        return s;
    }
    Num query(long i) { return query(cast(int)i); }
}

void solve() {
    int N, C; readf("%d %d\n", &N, &C);
    auto A = readarray!int;
    A = A.sort.uniq.array;
    N = A.length;

    bool f() {
        if (A[0] != 1) return false;
        auto M = new bool[C+1];
        foreach (a; A) M[a] = true;
        auto R = iota(1, C+1, 1).filter!(i => !M[i]).array;
        auto bit = BIT!(long, 0)(C+1);
        foreach (long r; R) {
            foreach (long a; A) {
                if (r * a > C) break;
                bit.add(r*a, 1);
                bit.add(r*a + a, -1);
            }
        }
        foreach (a; A) {
            if (bit.query(a+1) >= 1) return false;
        }
        return true;
    }
    writeln(f() ? "Yes" : "No");
}

void main() {
    int T = read!int;
    foreach (t; 0 .. T) solve();
}

import std.stdio;
import std.math;
import std.numeric;
import std.container;
import std.typecons;
import core.stdc.stdio : scanf;
import std.conv;
import std.array;
import std.string;
import std.range;
import std.algorithm;

T read(T)() { return readln.chomp.to!T; }
T[] readarray(T)() { return readln.chomp.split(" ").map!(to!T).array; }

struct SegmentTree(T, T unit, alias binop) {
    int n;
    T[] dat;
    this(int n_) {
        n = 1;
        while (n < n_) n *= 2;
        dat = new T[2*n+2];
        dat[] = unit;
    }
    void update(int k, in T a) {
        k += n - 1;
        dat[k] = a;
        while (k > 0) {
            k = (k - 1) / 2;
            dat[k] = binop(dat[k * 2 + 1], dat[k * 2 + 2]);
        }
    }
    T query(int a, int b) const {
        return query(a, b, 0, 0, n);
    }
    T query(int a, int b, int k, int l, int r) const {
        if (r <= a || b <= l) return unit;
        if (a <= l && r <= b) return dat[k];
        T vl = query(a, b, k * 2 + 1, l, (l + r) / 2),
          vr = query(a, b, k * 2 + 2, (l + r) / 2, r);
        return binop(vl, vr);
    }
}
alias RSQ = SegmentTree!(long, 0, (a, b) => a + b);

struct BIT(Num, Num zero) {
    int N;
    Num[] dat; // dat is 1-indexed
    this(int N) {
        this.N = N;
        dat = new Num[N + 1];
        dat[] = zero;
    }
    // add x to i-th (0-indexed) element
    void add(int i, Num x) {
        i++; // make 1-indexed
        while (i <= N) {
            dat[i] += x;
            i += i & -i;
        }
    }
    void add(long i, Num x) { add(cast(int)i, x); }
    // return the sum of [0, i) (0-indexed) element
    Num query(int i) {
        Num s = zero;
        while (i > 0) {
            s += dat[i];
            i -= i & -i;
        }
        return s;
    }
    Num query(long i) { return query(cast(int)i); }
}

/*
void solve() {
    int N, C; readf("%d %d\n", &N, &C);
    auto A = readarray!int;
    A = A.sort.uniq.array;
    N = A.length;
    bool f() {
        if (A[0] != 1) return false;
        if (N == 1) return true;
        auto P = RSQ(C+2);
        P.update(A[1], 1);
        P.update(A[1]+A[1], -1);
        P.update(min(C+1, A[1] * A[1]), 1);
        P.update(min(C+1, A[1] * A[1] + A[1]), -1);
        for (int i = 2; i < N; i++) {
            if (P.query(0, A[i]+1) <= 0) return false;
            for (int j = 0; j <= i; j++) {
                int L = A[i] * A[j];
                if (L > C) break;
                int R = min(C + 1, L + A[j]);
                P.update(L, 1);
                P.update(R, -1);
            }
        }
        return true;
    }
    writeln(f() ? "Yes" : "No");
}
*/

void solve() {
    int N, C; readf("%d %d\n", &N, &C);
    auto A = readarray!long;
    A = A.sort.uniq.array;
    N = A.length;

    bool f() {
        if (A[0] != 1) return false;
        if (N == 1) return true;
        auto P = BIT!(long, 0)(C+2);
        P.add(A[1], 1);
        P.add(A[1]+A[1], -1);
        P.add(min(C+1, A[1] * A[1]), 1);
        P.add(min(C+1, A[1] * A[1] + A[1]), -1);
        for (int i = 2; i < N; i++) {
            if (P.query(cast(int)(A[i]+1)) <= 0) return false;
            for (int j = 0; j <= i; j++) {
                long L = A[i] * A[j];
                if (L > C) break;
                long R = min(C + 1, L + A[j]);
                P.add(L, 1);
                P.add(R, -1);
            }
        }
        return true;
    }
    writeln(f() ? "Yes" : "No");
}

void main() {
    int T = read!int;
    foreach (t; 0 .. T) solve();
}

import std.stdio;
import std.math;
import std.numeric;
import std.container;
import std.typecons;
import core.stdc.stdio : scanf;
import std.conv;
import std.array;
import std.string;
import std.range;
import std.algorithm;

T read(T)() { return readln.chomp.to!T; }
T[] readarray(T)() { return readln.chomp.split(" ").map!(to!T).array; }

struct SegmentTree(T, T unit, alias binop) {
    int n;
    T[] dat;
    this(int n_) {
        n = 1;
        while (n < n_) n *= 2;
        dat = new T[2*n+2];
        dat[] = unit;
    }
    void update(int k, in T a) {
        k += n - 1;
        dat[k] = a;
        while (k > 0) {
            k = (k - 1) / 2;
            dat[k] = binop(dat[k * 2 + 1], dat[k * 2 + 2]);
        }
    }
    T query(int a, int b) const {
        return query(a, b, 0, 0, n);
    }
    T query(int a, int b, int k, int l, int r) const {
        if (r <= a || b <= l) return unit;
        if (a <= l && r <= b) return dat[k];
        T vl = query(a, b, k * 2 + 1, l, (l + r) / 2),
          vr = query(a, b, k * 2 + 2, (l + r) / 2, r);
        return binop(vl, vr);
    }
}
alias RSQ = SegmentTree!(long, 0, (a, b) => a + b);

struct BIT(Num, Num zero) {
    int N;
    Num[] dat; // dat is 1-indexed
    this(int N) {
        this.N = N;
        dat = new Num[N + 1];
        dat[] = zero;
    }
    // add x to i-th (0-indexed) element
    void add(int i, Num x) {
        i++; // make 1-indexed
        while (i <= N) {
            dat[i] += x;
            i += i & -i;
        }
    }
    // return the sum of [0, i) (0-indexed) element
    Num query(int i) {
        Num s = zero;
        while (i > 0) {
            s += dat[i];
            i -= i & -i;
        }
        return s;
    }
}

/*
void solve() {
    int N, C; readf("%d %d\n", &N, &C);
    auto A = readarray!int;
    A = A.sort.uniq.array;
    N = A.length;
    bool f() {
        if (A[0] != 1) return false;
        if (N == 1) return true;
        auto P = RSQ(C+2);
        P.update(A[1], 1);
        P.update(A[1]+A[1], -1);
        P.update(min(C+1, A[1] * A[1]), 1);
        P.update(min(C+1, A[1] * A[1] + A[1]), -1);
        for (int i = 2; i < N; i++) {
            if (P.query(0, A[i]+1) <= 0) return false;
            for (int j = 0; j <= i; j++) {
                int L = A[i] * A[j];
                if (L > C) break;
                int R = min(C + 1, L + A[j]);
                P.update(L, 1);
                P.update(R, -1);
            }
        }
        return true;
    }
    writeln(f() ? "Yes" : "No");
}
*/

void solve() {
    int N, C; readf("%d %d\n", &N, &C);
    auto A = readarray!int;
    A = A.sort.uniq.array;
    N = A.length;

    bool f() {
        if (A[0] != 1) return false;
        if (N == 1) return true;
        auto P = BIT!(int, 0)(C+2);
        P.add(A[1], 1);
        P.add(A[1]+A[1], -1);
        P.add(min(C+1, A[1] * A[1]), 1);
        P.add(min(C+1, A[1] * A[1] + A[1]), -1);
        for (int i = 2; i < N; i++) {
            if (P.query(A[i]+1) <= 0) return false;
            for (int j = 0; j <= i; j++) {
                int L = A[i] * A[j];
                if (L > C) break;
                int R = min(C + 1, L + A[j]);
                P.add(L, 1);
                P.add(R, -1);
            }
        }
        return true;
    }
    writeln(f() ? "Yes" : "No");
}

void main() {
    int T = read!int;
    foreach (t; 0 .. T) solve();
}


This is the harder version of the problem. In this version, $$$1 \le n \le 10^6$$$ and $$$0 \leq a_i \leq 10^6$$$. You can hack this problem if you locked it. But you can hack the previous problem only if you locked both problemsChristmas is coming, and our protagonist, Bob, is preparing a spectacular present for his long-time best friend Alice. This year, he decides to prepare $$$n$$$ boxes of chocolate, numbered from $$$1$$$ to $$$n$$$. Initially, the $$$i$$$-th box contains $$$a_i$$$ chocolate pieces.Since Bob is a typical nice guy, he will not send Alice $$$n$$$ empty boxes. In other words, at least one of $$$a_1, a_2, \ldots, a_n$$$ is positive. Since Alice dislikes coprime sets, she will be happy only if there exists some integer $$$k > 1$$$ such that the number of pieces in each box is divisible by $$$k$$$. Note that Alice won't mind if there exists some empty boxes. Charlie, Alice's boyfriend, also is Bob's second best friend, so he decides to help Bob by rearranging the chocolate pieces. In one second, Charlie can pick up a piece in box $$$i$$$ and put it into either box $$$i-1$$$ or box $$$i+1$$$ (if such boxes exist). Of course, he wants to help his friend as quickly as possible. Therefore, he asks you to calculate the minimum number of seconds he would need to make Alice happy.

The first line contains a single integer $$$n$$$ ($$$1 \le n \le 10^6$$$) — the number of chocolate boxes. The second line contains $$$n$$$ integers $$$a_1, a_2, \ldots, a_n$$$ ($$$0 \le a_i \le 10^6$$$) — the number of chocolate pieces in the $$$i$$$-th box. It is guaranteed that at least one of $$$a_1, a_2, \ldots, a_n$$$ is positive.

If there is no way for Charlie to make Alice happy, print $$$-1$$$. Otherwise, print a single integer $$$x$$$ — the minimum number of seconds for Charlie to help Bob make Alice happy.

NoteIn the first example, Charlie can move all chocolate pieces to the second box. Each box will be divisible by $$$17$$$.In the second example, Charlie can move a piece from box $$$2$$$ to box $$$3$$$ and a piece from box $$$4$$$ to box $$$5$$$. Each box will be divisible by $$$3$$$.In the third example, each box is already divisible by $$$5$$$.In the fourth example, since Charlie has no available move, he cannot help Bob make Alice happy.

import std.algorithm;
import std.conv;
import std.range;
import std.stdio;
import std.string;
import std.typecons;

void main ()
{
	int n;
	while (readf (" %s", &n) > 0)
	{
		readln;
		auto a = readln.splitter.map !(to !(int)).array;
		auto total = sum (a, 0L);
		if (total == 1)
		{
			writeln (-1);
			continue;
		}

		long [] p;
		for (long d = 2; d * d <= total; d++)
		{
			if (total % d == 0)
			{
				p ~= d;
				while (total % d == 0)
				{
					total /= d;
				}
			}
		}
		if (total > 1)
		{
			p ~= total;
		}

		long solve (long d)
		{
			long cur = 0;
			long res = 0;
			foreach (i; 0..n - 1)
			{
				cur += a[i];
				cur %= d;
				res += min (cur, d - cur);
			}
			return res;
		}

		long res = total * n;
		foreach (ref c; p)
		{
			res = min (res, solve (c));
		}
		writeln (res);
	}
}

import std.algorithm, std.conv, std.range, std.stdio;
void main () {
	int n;
	readf (" %s ", &n);
	auto a = readln.split.map !(to!int).array, t = sum (a, 0L);
	long [] p;
	for (long d = 2; d * d <= t; d++) {
		if (t % d < 1) {
			p ~= d;
			while (t % d < 1) t /= d;
		}
	}
	if (t > 1) p ~= t;
	long s (long d) {
		long c, r;
		foreach (i; 0..n - 1) {
			c += a[i];
			c %= d;
			r += min (c, d - c);
		}
		return r;
	}
	long z = long.max;
	foreach (ref c; p) z = min (z, s (c));
	writeln (z < long.max ? z : -1);
}

import std.stdio, std.conv, std.string, std.array, std.range, std.algorithm, std.container;
import std.math, std.random, std.bigint, std.datetime, std.format;
void main(string[] args){ if(args.length > 1) if(args[1] == "-debug") DEBUG = 1; solve(); }
void log()(){ writeln(""); } void log(T, A ...)(T t, lazy A a){ if(DEBUG) write(t, " "), log(a); } bool DEBUG = 0;
string rstring(){ static string[] ss; while(!ss.length) ss = readln.chomp.split; string res = ss[0]; ss.popFront; return res; }
T rtype(T)(){ return rstring.to!T; } alias rint = rtype!int, rlong = rtype!long, rreal = rtype!real;
T[] rtypes(T)(int n){ return n.iota.map!(i => rtype!T()).array; } alias rint = rtypes!int, rlong = rtypes!long, rreal = rtypes!real;
T[][] rtypess(T)(int n, int m){ return n.iota.map!(i => rtypes!T(m)).array; } alias rint = rtypess!int, rlong = rtypess!long, rreal = rtypess!real;

// ----- ----- ----- ----- ----- ----- ----- ----- ----- ----- ----- ----- //

void solve(){
	int n = rint;
	long[] as = rlong(n);

	long sum = as.sum;
	long[] ds;
	for(long d = 1; d * d <= sum; d ++) if(sum % d == 0) ds ~= d, ds ~= sum / d;
	log("as:", as, "sum:", sum, "ds:", ds);
	ds.sort();
	long[] d2s;
	A:
	foreach(d; ds){
		if(d == 1) continue;
		foreach(d2; d2s) if(d % d2 == 0) continue A;
		d2s ~= d;
	}
	ds = d2s;
	log("ds:", ds);

	long ans = as.sum * n;
	foreach(d; ds){
		long leftover;
		long tempans;
		long q;
		foreach(i, a; as){
			q += a, q %= d;
			if(q < d - q) tempans += q;
			else tempans += d - q;
			log("i:", i, "q:", q, "tempans:", tempans);
		}
		ans = min(ans, tempans);
		log("tempans:", tempans, "ans:", ans);
	}
	if(ans >= as.sum * n) ans = -1;
	ans.writeln;
}

import std.conv, std.functional, std.range, std.stdio, std.string;
import std.algorithm, std.array, std.bigint, std.bitmanip, std.complex, std.container, std.math, std.numeric, std.regex, std.typecons;
import core.bitop;

class EOFException : Throwable { this() { super("EOF"); } }
string[] tokens;
string readToken() { for (; tokens.empty; ) { if (stdin.eof) { throw new EOFException; } tokens = readln.split; } auto token = tokens.front; tokens.popFront; return token; }
int readInt() { return readToken.to!int; }
long readLong() { return readToken.to!long; }
real readReal() { return readToken.to!real; }

bool chmin(T)(ref T t, in T f) { if (t > f) { t = f; return true; } else { return false; } }
bool chmax(T)(ref T t, in T f) { if (t < f) { t = f; return true; } else { return false; } }

int binarySearch(alias pred, T)(in T[] as) { int lo = -1, hi = cast(int)(as.length); for (; lo + 1 < hi; ) { const mid = (lo + hi) >> 1; (unaryFun!pred(as[mid]) ? hi : lo) = mid; } return hi; }
int lowerBound(T)(in T[] as, T val) { return as.binarySearch!(a => (a >= val)); }
int upperBound(T)(in T[] as, T val) { return as.binarySearch!(a => (a > val)); }

enum INF = 10L^^18;

void main() {
  try {
    for (; ; ) {
      const N = readInt();
      auto A = new long[N];
      foreach (i; 0 .. N) {
        A[i] = readLong();
      }

      const S = A.sum;
      long[] ps;
      long s = S;
      for (long p = 2; p * p <= s; ++p) {
        if (s % p == 0) {
          do {
            s /= p;
          } while (s % p == 0);
          ps ~= p;
        }
      }
      if (s > 1) {
        ps ~= s;
      }
      debug {
        writeln("ps = ", ps);
      }

      long ans = INF;
      foreach (p; ps) {
        long cost;
        long now;
        foreach (i; 0 .. N) {
          now += A[i];
          now %= p;
          cost += min(now, p - now);
        }
        debug {
          writeln(p, ": ", cost);
        }
        chmin(ans, cost);
      }
      writeln((ans >= INF) ? -1 : ans);
    }
  } catch (EOFException e) {
  }
}