Problem:
Score : 1600 points

Problem Statement

Snuke has permutations (P_0,P_1,\cdots,P_{N-1}) and (Q_0,Q_1,\cdots,Q_{N-1}) of (0,1,\cdots,N-1).

Now, he will make new permutations A and B of (0,1,\cdots,N-1), under the following conditions:

For each i (0 \leq i \leq N-1), A_i should be i or P_i.

For each i (0 \leq i \leq N-1), B_i should be i or Q_i.

Let us define the distance of permutations A and B as the number of indices i such that A_i \neq B_i.
Find the maximum possible distance of A and B.

Constraints

1 \leq N \leq 100000

0 \leq P_i \leq N-1

P_0,P_1,\cdots,P_{N-1} are all different.

0 \leq Q_i \leq N-1

Q_0,Q_1,\cdots,Q_{N-1} are all different.

All values in input are integers.

Input

Input is given from Standard Input in the following format:

N
P_0 P_1 \cdots P_{N-1}
Q_0 Q_1 \cdots Q_{N-1}

Output

Print the maximum possible distance of A and B.

Sample Input 1

4
2 1 3 0
0 2 3 1

Sample Output 1

3

For example, if we make A=(0,1,2,3) and B=(0,2,3,1), the distance will be 3, which is the maximum result possible.

Sample Input 2

10
0 4 5 3 7 8 2 1 9 6
3 8 5 6 4 0 2 1 7 9

Sample Output 2

8

Sample Input 3

32
22 31 30 29 7 17 16 3 14 9 19 11 2 5 10 1 25 18 15 24 20 0 12 21 27 4 26 28 8 6 23 13
22 3 2 7 17 9 16 4 14 8 19 26 28 5 10 1 25 18 15 13 11 0 12 23 21 20 29 24 27 6 30 31

Sample Output 3

28

Solution in C++14 (GCC 5.4.1) (judge verdict: Time Limit Exceeded)

#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
const int maxn = 100000 + 10;
//const int maxn = 100 + 10;
const int N = maxn << 1;
const int maxE = maxn << 3;
const int INF = 0x3f3f3f3f;

int n, a[maxn], b[maxn], pos1[maxn], pos2[maxn], vis[maxn];
int S, T, h[N], ecnt;
struct enode{
	int v, n, w, op;
	enode() {}
	enode(int _v, int _n, int _w, int _op):v(_v), n(_n), w(_w), op(_op) {}
}e[maxE];

inline void addedge(int u, int v, int w) {
//	cout << u << ' ' << v << ' ' << w << endl;
	ecnt ++; e[ecnt] = enode(v,h[u],w,ecnt + 1); h[u] = ecnt;
	ecnt ++; e[ecnt] = enode(u,h[v],0,ecnt - 1); h[v] = ecnt;
}

inline void init(int *a, int *pos) {
	memset(vis,0,sizeof(vis)); int cnt = 0;
	for(int i = 1;i <= n;i ++) {
		if(vis[i]) continue; 
		cnt ++;
		for(int p = i;!vis[p];p = a[p]) {
      pos[p] = cnt;
			vis[p] = 1;
		}
	}
}

int level[N], q[N << 1];
inline bool bfs() {
  memset(level,0,sizeof(level));
	int head = 1, tail = 0;
	q[++ tail] = S; level[S] = 1;
	while(head <= tail) {
		int u = q[head]; head ++;
		for(int i = h[u];~ i;i = e[i].n) {
			int v = e[i].v;
			if(!level[v] && e[i].w > 0) {
				level[v] = level[u] + 1;
				q[++ tail] = v;
				if(v == T) return 1;
			}
		}
	}
	return 0;
}

int dfs(int u, int c) {
	if(u == T || c == 0) return c;
	int tmp = 0;
	for(int i = h[u];~ i;i = e[i].n) {
		int v = e[i].v;
		if(level[v] == level[u] + 1) {
			int x = dfs(v,min(c,e[i].w));
			if(x) {
				tmp += x; c -= x;
				e[i].w -= x; e[e[i].op].w += x;
				if(!c) break;
			}
		}
	}
	if(!tmp) level[u] = -1;
	return tmp;
}

inline int max_flow() {
  int now = 0;
	while(bfs())
		now += dfs(S,INF);
	return now;
}

int main() {
//	freopen("data.in","r",stdin);
  scanf("%d", &n); ecnt = 0;
	memset(h,-1,sizeof(h));
	for(int i = 1;i <= n;i ++) scanf("%d", &a[i]), a[i] ++;
	for(int i = 1;i <= n;i ++) scanf("%d", &b[i]), b[i] ++;
  init(a,pos1);
  init(b,pos2);
	for(int i = 1;i <= n;i ++) pos2[i] += n;
	int Ans = 0; S = n + n + 1, T = S + 1;
	for(int i = 1;i <= n;i ++) if(a[i] != b[i]) Ans ++;
	for(int i = 1;i <= n;i ++) {
//    cout << "work " << i << endl;
		if(a[i] == b[i]) {
			if(a[i] == i) continue;
			else {
				Ans ++;
				addedge(pos1[i],pos2[i],1);
				addedge(pos2[i],pos1[i],1);
			}
		}
		else {
			if(a[i] == i) addedge(S,pos2[i],1);
			else if(b[i] == i) addedge(pos1[i],T,1);
			else addedge(pos1[i],pos2[i],1);
		}
	}
	int now = max_flow();
	Ans -= now;
	printf("%d\n", Ans);
	return 0;
}