이 제출은 이전 버전의 oj.uz에서 채점하였습니다. 현재는 제출 당시와는 다른 서버에서 채점을 하기 때문에, 다시 제출하면 결과가 달라질 수도 있습니다.
import java.io.OutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.PrintWriter;
import java.io.DataInputStream;
import java.io.IOException;
import java.io.FileInputStream;
import java.io.InputStreamReader;
import java.util.Stack;
import java.util.ArrayList;
import java.util.Vector;
import java.util.StringTokenizer;
import java.io.BufferedReader;
import java.io.InputStream;
/**
* Built using CHelper plug-in
* Actual solution is at the top
*/
public class net {
public static void main(String[] args) {
InputStream inputStream = System.in;
OutputStream outputStream = System.out;
InputReader in = new InputReader(inputStream);
PrintWriter out = new PrintWriter(outputStream);
Network solver = new Network();
solver.solve(1, in, out);
out.close();
}
static class Network {
int[][] adj;
ArrayList<Set> ans = new ArrayList<>();
public void solve(int testNumber, InputReader in, PrintWriter out) {
try {
Network.Reader r = new Network.Reader();
int N = r.nextInt();
adj = new int[N][];
int[] from = new int[N - 1];
int[] to = new int[N - 1];
for (int i = 0; i < N - 1; i++) {
int a = r.nextInt() - 1;
int b = r.nextInt() - 1;
from[i] = a;
to[i] = b;
}
adj = DefaultTree.packU(N, from, to);
if (N == 2) {
out.println("1\n1 2");
} else {
for (int i = 0; i < N; i++) {
if (adj[i].length > 1) {
Set f = dfs(i);
if (f.a2 == -1) {
ans.add(new Set(f.a1, i));
} else {
ans.add(new Set(f.a1, f.a2));
}
break;
}
}
out.println(ans.size());
for (Set s : ans) {
out.println((s.a1 + 1) + " " + (s.a2 + 1));
}
}
} catch (IOException e) {
}
}
Set dfs(int n) {
Stack<State> stack = new Stack<>();
stack.add(new State(n, n));
while (stack.size() > 0) {
State next = stack.peek();
int a = next.getNext();
if (a == -1) {
stack.pop();
if (stack.isEmpty()) {
return next.s;
}
if (next.cur == 1) {
stack.peek().merge(new Set(next.n));
} else {
stack.peek().merge(next.s);
}
} else {
stack.add(new State(a, next.n));
}
}
return null;
}
class State {
int cur;
int n;
int p;
Set s = null;
State(int n, int p) {
cur = 0;
this.n = n;
this.p = p;
}
int getNext() {
if (cur >= adj[n].length) {
return -1;
} else if (adj[n][cur] == p) {
cur++;
return getNext();
} else {
return adj[n][cur++];
}
}
void merge(Set s) {
if (this.s == null) {
this.s = s;
} else {
this.s.merge(s);
}
}
}
class Set {
int a1;
int a2;
void merge(Set s) {
if (s.a2 == -1 && this.a2 == -1) {
this.a2 = s.a1;
} else if (s.a2 == -1) {
ans.add(new Set(s.a1, this.a2));
this.a2 = -1;
} else if (this.a2 == -1) {
ans.add(new Set(this.a1, s.a2));
this.a1 = s.a1;
} else {
ans.add(new Set(this.a1, s.a1));
this.a1 = this.a2;
this.a2 = s.a2;
}
}
Set(int a) {
this.a1 = a;
this.a2 = -1;
}
Set(int a, int b) {
this.a1 = a;
this.a2 = b;
}
}
static class Reader {
final private int BUFFER_SIZE = 1 << 16;
private DataInputStream din;
private byte[] buffer;
private int bufferPointer;
private int bytesRead;
public Reader() {
din = new DataInputStream(System.in);
buffer = new byte[BUFFER_SIZE];
bufferPointer = bytesRead = 0;
}
public Reader(String file_name) throws IOException {
din = new DataInputStream(new FileInputStream(file_name));
buffer = new byte[BUFFER_SIZE];
bufferPointer = bytesRead = 0;
}
public int nextInt() throws IOException {
int ret = 0;
byte c = read();
while (c <= ' ')
c = read();
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 void fillBuffer() throws IOException {
bytesRead = din.read(buffer, bufferPointer = 0, BUFFER_SIZE);
if (bytesRead == -1)
buffer[0] = -1;
}
private byte read() throws IOException {
if (bufferPointer == bytesRead)
fillBuffer();
return buffer[bufferPointer++];
}
}
}
static class DefaultTree {
DefaultTree.Node[] tree;
int K;
int[][] lift;
int[] tin;
int[] tout;
public DefaultTree(int N) {
tree = new DefaultTree.Node[N];
K = (int) Math.ceil(Math.log(N) / Math.log(2)) + 1;
lift = new int[N][K];
tin = new int[N];
tout = new int[N];
for (int i = 0; i < N; i++) {
tree[i] = new DefaultTree.Node();
}
}
public static int[][] packU(int N, int[] from, int[] to) {
//undirected
int[][] adj = new int[N][];
int[] cntFrom = new int[N];
for (int i = 0; i < from.length; i++) {
cntFrom[from[i]]++;
cntFrom[to[i]]++;
}
for (int i = 0; i < N; i++) {
adj[i] = new int[cntFrom[i]];
}
for (int i = 0; i < from.length; i++) {
adj[from[i]][--cntFrom[from[i]]] = to[i];
adj[to[i]][--cntFrom[to[i]]] = from[i];
}
return adj;
}
static class Node {
}
}
static class InputReader {
public BufferedReader reader;
public StringTokenizer tokenizer;
public InputReader(InputStream stream) {
reader = new BufferedReader(new InputStreamReader(stream), 32768);
tokenizer = null;
}
}
}
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |