Problem: Johnny's younger sister Megan had a birthday recently. Her brother has bought her a box signed as "Your beautiful necklace — do it yourself!". It contains many necklace parts and some magic glue. 

The necklace part is a chain connecting two pearls. Color of each pearl can be defined by a non-negative integer. The magic glue allows Megan to merge two pearls (possibly from the same necklace part) into one. The beauty of a connection of pearls in colors u and v is defined as follows: let 2^k be the greatest power of two dividing u ⊕ v — [exclusive or](https://en.wikipedia.org/wiki/Exclusive_or#Computer_science) of u and v. Then the beauty equals k. If u = v, you may assume that beauty is equal to 20.

Each pearl can be combined with another at most once. Merging two parts of a necklace connects them. Using the glue multiple times, Megan can finally build the necklace, which is a cycle made from connected necklace parts (so every pearl in the necklace is combined with precisely one other pearl in it). The beauty of such a necklace is the minimum beauty of a single connection in it. The girl wants to use all available necklace parts to build exactly one necklace consisting of all of them with the largest possible beauty. Help her!

Input

The first line contains n (1 ≤ n ≤ 5 ⋅ 10^5) — the number of necklace parts in the box. Each of the next n lines contains two integers a and b (0 ≤ a, b < 2^{20}), which denote colors of pearls presented in the necklace parts. Pearls in the i-th line have indices 2i - 1 and 2i respectively.

Output

The first line should contain a single integer b denoting the maximum possible beauty of a necklace built from all given parts.

The following line should contain 2n distinct integers p_i (1 ≤ p_i ≤ 2n) — the indices of initial pearls in the order in which they appear on a cycle. Indices of pearls belonging to the same necklace part have to appear at neighboring positions in this permutation (so 1 4 3 2 is not a valid output, whereas 2 1 4 3 and 4 3 1 2 are). If there are many possible answers, you can print any.

Examples

Input


5
13 11
11 1
3 5
17 1
9 27


Output


3
8 7 9 10 5 6 1 2 3 4 


Input


5
13 11
11 1
3 5
17 1
7 29


Output


2
8 7 10 9 5 6 4 3 2 1 


Input


1
1 1


Output


20
2 1 

Note

In the first example the following pairs of pearls are combined: (7, 9), (10, 5), (6, 1), (2, 3) and (4, 8). The beauties of connections equal correspondingly: 3, 3, 3, 20, 20.

The following drawing shows this construction.

<image>

Solution (in JAVA):

Solution:
import java.io.*;
import java.util.HashMap;
import java.util.InputMismatchException;

/**
 * Built using CHelper plug-in
 * Actual solution is at the top
 */
public class Main {
	static class TaskAdapter implements Runnable {
		@Override
		public void run() {
			long startTime = System.currentTimeMillis();
			InputStream inputStream = System.in;
			OutputStream outputStream = System.out;
			FastReader in = new FastReader(inputStream);
			Output out = new Output(outputStream);
			CJohnnyAndMegansNecklace solver = new CJohnnyAndMegansNecklace();
			solver.solve(1, in, out);
			out.close();
			System.err.println(System.currentTimeMillis()-startTime+"ms");
		}
	}

	public static void main(String[] args) throws Exception {
		Thread thread = new Thread(null, new TaskAdapter(), "", 1<<28);
		thread.start();
		thread.join();
	}

	static class CJohnnyAndMegansNecklace {
		int n;
		int ind;
		int[] tour;
		int[][] arr;
		boolean[] used;
		CJohnnyAndMegansNecklace.Stack[] graph;

		public CJohnnyAndMegansNecklace() {
		}

		public void tour(int u) {
			CJohnnyAndMegansNecklace.Stack s = new CJohnnyAndMegansNecklace.Stack(2*n);
			s.addLast(u);
			while(!s.isEmpty()) {
				int cur = s.removeLast();
				while(!graph[cur].isEmpty()) {
					int i = graph[cur].removeLast();
					if(!used[i]) {
						used[i] = true;
						s.addLast(cur);
						cur = arr[i][0]==cur ? arr[i][1] : arr[i][0];
					}
				}
				tour[ind++] = cur;
			}
		}

		public boolean valid(int x) {
			x = (1<<x)-1;
			int n = x+1;
			int[] cnt = new int[n];
			for(int i = 0; i<this.n; i++) {
				cnt[arr[i][0]&x]++;
				cnt[arr[i][1]&x]++;
			}
			for(int i = 0; i<n; i++) {
				if(Utilities.odd(cnt[i])) {
					return false;
				}
			}
			int[] ind = new int[n];
			int[][] graph = new int[n][];
			for(int i = 0; i<n; i++) {
				graph[i] = new int[cnt[i]];
			}
			for(int i = 0; i<this.n; i++) {
				int u = arr[i][0]&x, v = arr[i][1]&x;
				graph[u][ind[u]++] = v;
				graph[v][ind[v]++] = u;
			}
			boolean[] visited = new boolean[n];
			CJohnnyAndMegansNecklace.Stack s = new CJohnnyAndMegansNecklace.Stack(n);
			for(int i = 0; i<n; i++) {
				if(cnt[i]>0) {
					s.addLast(i);
					visited[i] = true;
					break;
				}
			}
			while(!s.isEmpty()) {
				int u = s.removeLast();
				for(int v: graph[u]) {
					if(!visited[v]) {
						s.addLast(v);
						visited[v] = true;
					}
				}
			}
			for(int i = 0; i<n; i++) {
				if(!visited[i]&&cnt[i]>0) {
					return false;
				}
			}
			return true;
		}

		public void solve(int kase, InputReader in, Output pw) {
			n = in.nextInt();
			arr = in.nextInt(n, 2);
			int l = 0, r = 20;
			while(l<r) {
				int mid = (l+r+1)/2;
				if(valid(mid)) {
					l = mid;
				}else {
					r = mid-1;
				}
			}
			pw.println(l);
			int x = 1<<l;
			graph = new CJohnnyAndMegansNecklace.Stack[x];
			for(int i = 0; i<x; i++) {
				graph[i] = new CJohnnyAndMegansNecklace.Stack(20);
			}
			x--;
			HashMap<CJohnnyAndMegansNecklace.Pair, CJohnnyAndMegansNecklace.Stack> edges = new HashMap<>(4*n);
			for(int i = 0; i<n; i++) {
				int u = arr[i][0] &= x, v = arr[i][1] &= x;
				graph[u].addLast(i);
				if(u!=v) {
					graph[v].addLast(i);
				}
				int finalI = i;
				edges.compute(new CJohnnyAndMegansNecklace.Pair(u, v), (a, b) -> {
					if(b==null) {
						b = new CJohnnyAndMegansNecklace.Stack(20);
					}
					b.addLast(finalI);
					return b;
				});
				edges.compute(new CJohnnyAndMegansNecklace.Pair(v, u), (a, b) -> {
					if(b==null) {
						b = new CJohnnyAndMegansNecklace.Stack(20);
					}
					b.addLast(finalI);
					return b;
				});
			}
			ind = 0;
			tour = new int[2*n];
			used = new boolean[n];
			for(int i = 0; i<=x; i++) {
				if(!graph[i].isEmpty()) {
					tour(i);
					break;
				}
			}
			boolean[] used = new boolean[n];
			for(int i = 0; i<n; i++) {
				var cur = edges.get(new CJohnnyAndMegansNecklace.Pair(tour[i], tour[i+1]));
				int j;
				while(used[j = cur.removeLast()]) ;
				used[j] = true;
				int u = j*2+1, v = j*2+2;
				if((arr[j][0]&x)==tour[i]) {
					pw.print(u+" "+v+" ");
				}else {
					pw.print(v+" "+u+" ");
				}
			}
		}

		static class Pair {
			int a;
			int b;

			public Pair(int a, int b) {
				this.a = a;
				this.b = b;
			}

			public boolean equals(Object o) {
				if(this==o) return true;
				if(o==null||getClass()!=o.getClass()) return false;
				CJohnnyAndMegansNecklace.Pair pair = (CJohnnyAndMegansNecklace.Pair) o;
				return a==pair.a&&b==pair.b;
			}

			public int hashCode() {
				return a*31+b;
			}

		}

		static class Stack {
			int n;
			int ind;
			int[] arr;

			public Stack(int n) {
				this.n = n;
				ind = 0;
				arr = new int[n];
			}

			public void addLast(int x) {
				if(ind>=n) {
					int[] narr = new int[2*n];
					System.arraycopy(arr, 0, narr, 0, n);
					n *= 2;
					arr = narr;
				}
				arr[ind++] = x;
			}

			public int removeLast() {
				return arr[--ind];
			}

			public boolean isEmpty() {
				return ind==0;
			}

		}

	}

	static class Utilities {
		public static boolean odd(int x) {
			return (x&1)>0;
		}

	}

	static class FastReader implements InputReader {
		final private int BUFFER_SIZE = 1<<16;
		private final DataInputStream din;
		private final byte[] buffer;
		private int bufferPointer;
		private int bytesRead;

		public FastReader(InputStream is) {
			din = new DataInputStream(is);
			buffer = new byte[BUFFER_SIZE];
			bufferPointer = bytesRead = 0;
		}

		public int nextInt() {
			int ret = 0;
			byte c = skipToDigit();
			boolean neg = (c=='-');
			if(neg) {
				c = read();
			}
			do {
				ret = ret*10+c-'0';
			} while((c = read())>='0'&&c<='9');
			if(neg) {
				return -ret;
			}
			return ret;
		}

		private boolean isDigit(byte b) {
			return b>='0'&&b<='9';
		}

		private byte skipToDigit() {
			byte ret;
			while(!isDigit(ret = read())&&ret!='-') ;
			return ret;
		}

		private void fillBuffer() {
			try {
				bytesRead = din.read(buffer, bufferPointer = 0, BUFFER_SIZE);
			}catch(IOException e) {
				e.printStackTrace();
				throw new InputMismatchException();
			}
			if(bytesRead==-1) {
				buffer[0] = -1;
			}
		}

		private byte read() {
			if(bytesRead==-1) {
				throw new InputMismatchException();
			}else if(bufferPointer==bytesRead) {
				fillBuffer();
			}
			return buffer[bufferPointer++];
		}

	}

	static class Output implements Closeable, Flushable {
		public StringBuilder sb;
		public OutputStream os;
		public int BUFFER_SIZE;
		public String lineSeparator;

		public Output(OutputStream os) {
			this(os, 1<<16);
		}

		public Output(OutputStream os, int bs) {
			BUFFER_SIZE = bs;
			sb = new StringBuilder(BUFFER_SIZE);
			this.os = new BufferedOutputStream(os, 1<<17);
			lineSeparator = System.lineSeparator();
		}

		public void print(String s) {
			sb.append(s);
			if(sb.length()>BUFFER_SIZE >> 1) {
				flushToBuffer();
			}
		}

		public void println(int i) {
			println(String.valueOf(i));
		}

		public void println(String s) {
			sb.append(s);
			println();
		}

		public void println() {
			sb.append(lineSeparator);
		}

		private void flushToBuffer() {
			try {
				os.write(sb.toString().getBytes());
			}catch(IOException e) {
				e.printStackTrace();
			}
			sb = new StringBuilder(BUFFER_SIZE);
		}

		public void flush() {
			try {
				flushToBuffer();
				os.flush();
			}catch(IOException e) {
				e.printStackTrace();
			}
		}

		public void close() {
			flush();
			try {
				os.close();
			}catch(IOException e) {
				e.printStackTrace();
			}
		}

	}

	interface InputReader {
		int nextInt();

		default int[] nextInt(int n) {
			int[] ret = new int[n];
			for(int i = 0; i<n; i++) {
				ret[i] = nextInt();
			}
			return ret;
		}

		default int[][] nextInt(int n, int m) {
			int[][] ret = new int[n][m];
			for(int i = 0; i<n; i++) {
				ret[i] = nextInt(m);
			}
			return ret;
		}

	}
}