You are given an array a consisting of n non-negative integers.

You have to replace each 0 in a with an integer from 1 to n (different elements equal to 0 can be replaced by different integers).

The value of the array you obtain is the number of integers k from 1 to n such that the following condition holds: there exist a pair of adjacent elements equal to k (i. e. there exists some i ∈ [1, n - 1] such that a_i = a_{i + 1} = k). If there are multiple such pairs for some integer k, this integer is counted in the value only once.

Your task is to obtain the array with the maximum possible value.

Input

The first line contains one integer n (2 ≤ n ≤ 3 ⋅ 10^5) — the number of elements in the array.

The second line contains n integers a_1, a_2, ..., a_n (0 ≤ a_i ≤ min(n, 600)) — the elements of the array.

Output

Print n integers not less than 1 and not greater than n — the array with the maximum possible value you can obtain.

If there are multiple answers, print any of them.

Examples

Input


4
1 1 0 2


Output


1 1 2 2 


Input


5
0 0 0 0 0


Output


3 1 1 3 3


Input


5
1 2 3 4 5


Output


1 2 3 4 5 


Input


6
1 0 0 0 0 1


Output


1 2 3 3 1 1


Input


3
3 0 2


Output


3 2 2 


Input


5
1 0 2 0 1


Output


1 2 2 1 1 


Input


7
1 0 2 3 1 0 2


Output


1 2 2 3 1 1 2 
20
1 0 4 3 0 0 0 2 1 0 0 4 2 0 0 4 2 0 0 3
 5
0 0 0 0 0
 14
0 14 4 1 0 4 9 0 0 0 8 4 0 1
 6
1 0 0 0 0 1
 100
0 0 77 89 33 93 0 0 0 40 0 2 93 56 0 60 94 0 2 43 0 82 43 74 4 59 80 9 73 7 33 90 5 12 0 96 0 37 0 72 62 0 59 0 0 0 0 71 26 22 24 0 0 0 0 34 86 87 13 0 0 1 77 0 99 0 0 65 97 6 14 0 0 0 0 59 73 0 0 18 0 3 76 39 52 0 0 56 0 0 58 0 84 0 95 0 0 0 58 0
 12
11 10 0 12 5 2 0 6 0 2 6 2
 16
0 0 0 15 16 0 0 4 2 0 13 0 0 13 0 2
 9
5 1 0 2 0 1 4 0 7

1 1 4 3 3 5 5 2 1 6 6 4 2 2 4 4 2 7 7 3 
 1 1 2 2 1 
 14 14 4 1 1 4 9 9 2 2 8 4 4 1
 1 1 1 2 2 1 
 4 4 77 89 33 93 93 5 5 40 40 2 93 56 60 60 94 2 2 43 43 82 43 74 4 59 80 9 73 7 33 90 5 12 12 96 37 37 72 72 62 62 59 6 6 7 7 71 26 22 24 24 8 8 34 34 86 87 13 13 1 1 77 77 99 99 65 65 97 6 14 14 9 9 59 59 73 73 18 18 3 3 76 39 52 52 56 56 10 10 58 84 84 1 95 95 11 11 58 58 
 11 10 10 12 5 2 2 6 6 2 6 2 
 1 1 15 15 16 16 4 4 2 2 13 3 3 13 13 2 
 5 1 1 2 2 1 4 4 7 

#ifndef LOCAL
#pragma GCC optimize ("Ofast")
#pragma GCC optimize ("unroll-loops")
#endif

#include <bits/stdc++.h>
using namespace std;

using ll=long long;
//#define int ll

#define rng(i,a,b) for(int i=int(a);i<int(b);i++)
#define rep(i,b) rng(i,0,b)
#define gnr(i,a,b) for(int i=int(b)-1;i>=int(a);i--)
#define per(i,b) gnr(i,0,b)
#define pb push_back
#define eb emplace_back
#define a first
#define b second
#define bg begin()
#define ed end()
#define all(x) x.bg,x.ed
#define si(x) int(x.size())
#ifdef LOCAL
#define dmp(x) cerr<<__LINE__<<" "<<#x<<" "<<x<<endl
#else
#define dmp(x) void(0)
#endif

template<class t,class u> bool chmax(t&a,u b){if(a<b){a=b;return true;}else return false;}
template<class t,class u> bool chmin(t&a,u b){if(b<a){a=b;return true;}else return false;}

template<class t> using vc=vector<t>;
template<class t> using vvc=vc<vc<t>>;

using pi=pair<int,int>;
using vi=vc<int>;

template<class t,class u>
ostream& operator<<(ostream& os,const pair<t,u>& p){
	return os<<"{"<<p.a<<","<<p.b<<"}";
}

template<class t> ostream& operator<<(ostream& os,const vc<t>& v){
	os<<"{";
	for(auto e:v)os<<e<<",";
	return os<<"}";
}

#define mp make_pair
#define mt make_tuple
#define one(x) memset(x,-1,sizeof(x))
#define zero(x) memset(x,0,sizeof(x))
#ifdef LOCAL
void dmpr(ostream&os){os<<endl;}
template<class T,class... Args>
void dmpr(ostream&os,const T&t,const Args&... args){
	os<<t<<" ";
	dmpr(os,args...);
}
#define dmp2(...) dmpr(cerr,__LINE__,##__VA_ARGS__)
#else
#define dmp2(...) void(0)
#endif

using uint=unsigned;
using ull=unsigned long long;

template<class t,size_t n>
ostream& operator<<(ostream&os,const array<t,n>&a){
	return os<<vc<t>(all(a));
}

template<int i,class T>
void print_tuple(ostream&,const T&){
}

template<int i,class T,class H,class ...Args>
void print_tuple(ostream&os,const T&t){
	if(i)os<<",";
	os<<get<i>(t);
	print_tuple<i+1,T,Args...>(os,t);
}

template<class ...Args>
ostream& operator<<(ostream&os,const tuple<Args...>&t){
	os<<"{";
	print_tuple<0,tuple<Args...>,Args...>(os,t);
	return os<<"}";
}

template<class t>
void print(t x,int suc=1){
	cout<<x;
	if(suc==1)
		cout<<"\n";
	if(suc==2)
		cout<<" ";
}

ll read(){
	ll i;
	cin>>i;
	return i;
}

vi readvi(int n,int off=0){
	vi v(n);
	rep(i,n)v[i]=read()+off;
	return v;
}

pi readpi(int off=0){
	int a,b;cin>>a>>b;
	return pi(a+off,b+off);
}

template<class t,class u>
void print(const pair<t,u>&p,int suc=1){
	print(p.a,2);
	print(p.b,suc);
}

template<class T>
void print(const vector<T>&v,int suc=1){
	rep(i,v.size())
		print(v[i],i==int(v.size())-1?suc:2);
}

template<class T>
void print_offset(const vector<T>&v,ll off,int suc=1){
	rep(i,v.size())
		print(v[i]+off,i==int(v.size())-1?suc:2);
}

template<class T,size_t N>
void print(const array<T,N>&v,int suc=1){
	rep(i,N)
		print(v[i],i==int(N)-1?suc:2);
}

string readString(){
	string s;
	cin>>s;
	return s;
}

template<class T>
T sq(const T& t){
	return t*t;
}

//#define CAPITAL
void yes(bool ex=true){
	#ifdef CAPITAL
	cout<<"YES"<<"\n";
	#else
	cout<<"Yes"<<"\n";
	#endif
	if(ex)exit(0);
	#ifdef LOCAL
	cout.flush();
	#endif
}
void no(bool ex=true){
	#ifdef CAPITAL
	cout<<"NO"<<"\n";
	#else
	cout<<"No"<<"\n";
	#endif
	if(ex)exit(0);
	#ifdef LOCAL
	cout.flush();
	#endif
}
void possible(bool ex=true){
	#ifdef CAPITAL
	cout<<"POSSIBLE"<<"\n";
	#else
	cout<<"Possible"<<"\n";
	#endif
	if(ex)exit(0);
	#ifdef LOCAL
	cout.flush();
	#endif
}
void impossible(bool ex=true){
	#ifdef CAPITAL
	cout<<"IMPOSSIBLE"<<"\n";
	#else
	cout<<"Impossible"<<"\n";
	#endif
	if(ex)exit(0);
	#ifdef LOCAL
	cout.flush();
	#endif
}

constexpr ll ten(int n){
	return n==0?1:ten(n-1)*10;
}

const ll infLL=LLONG_MAX/3;

#ifdef int
const int inf=infLL;
#else
const int inf=INT_MAX/2-100;
#endif

int topbit(signed t){
	return t==0?-1:31-__builtin_clz(t);
}
int topbit(ll t){
	return t==0?-1:63-__builtin_clzll(t);
}
int botbit(signed a){
	return a==0?32:__builtin_ctz(a);
}
int botbit(ll a){
	return a==0?64:__builtin_ctzll(a);
}
int popcount(signed t){
	return __builtin_popcount(t);
}
int popcount(ll t){
	return __builtin_popcountll(t);
}
bool ispow2(int i){
	return i&&(i&-i)==i;
}
ll mask(int i){
	return (ll(1)<<i)-1;
}

bool inc(int a,int b,int c){
	return a<=b&&b<=c;
}

template<class t> void mkuni(vc<t>&v){
	sort(all(v));
	v.erase(unique(all(v)),v.ed);
}

ll rand_int(ll l, ll r) { //[l, r]
	#ifdef LOCAL
	static mt19937_64 gen;
	#else
	static mt19937_64 gen(chrono::steady_clock::now().time_since_epoch().count());
	#endif
	return uniform_int_distribution<ll>(l, r)(gen);
}

template<class t>
void myshuffle(vc<t>&a){
	rep(i,si(a))swap(a[i],a[rand_int(0,i)]);
}

template<class t>
int lwb(const vc<t>&v,const t&a){
	return lower_bound(all(v),a)-v.bg;
}

vvc<int> readGraph(int n,int m){
	vvc<int> g(n);
	rep(i,m){
		int a,b;
		cin>>a>>b;
		//sc.read(a,b);
		a--;b--;
		g[a].pb(b);
		g[b].pb(a);
	}
	return g;
}

vvc<int> readTree(int n){
	return readGraph(n,n-1);
}

//sz: size of the matching
//mt[i]: matching mate of the vertex i
//VERIFY: yosupo
//NEERC2018B
//Petrozavodsk 2019w Day1 A
struct maxmatching{
	struct E{int a,b;};
	const vvc<int>&g;
	int n,sz;
	vi p,t,mt;
	vc<E> f;
	int non(int v){
		return t[v]!=sz||p[v]==-1?v:(p[v]=non(p[v]));
	}
	void R(int a,int b){
		int d=mt[a];
		mt[a]=b;
		if(d==-1||mt[d]!=a)return;
		if(f[a].b==-1){
			mt[d]=f[a].a;
			R(f[a].a,d);
		}else{
			R(f[a].a,f[a].b);
			R(f[a].b,f[a].a);
		}
	}
	bool arg(int rt){
		queue<int> q;
		t[rt]=sz;
		p[rt]=-1;
		f[rt]=E{-1,-1};
		q.push(rt);
		while(!q.empty()){
			int a=q.front();q.pop();
			for(auto b:g[a]){
				if(b==rt)continue;
				if(mt[b]==-1){
					mt[b]=a;
					R(a,b);
					return true;
				}
				if(t[b]==sz){
					int x=non(a),y=non(b);
					if(x==y)continue;
					int z=rt;
					while(x!=rt||y!=rt){
						if(y!=rt)swap(x,y);
						if(f[x].a==a&&f[x].b==b){
							z=x;
							break;
						}
						f[x]=E{a,b};
						x=non(f[mt[x]].a);
					}
					for(auto v:{non(a),non(b)}){
						while(v!=z){
							t[v]=sz;
							p[v]=z;
							q.push(v);
							v=non(f[mt[v]].a);
						}
					}
					continue;
				}
				if(t[mt[b]]==sz)continue;
				f[b]=E{-1,-1};
				t[mt[b]]=sz;
				p[mt[b]]=b;
				f[mt[b]]=E{a,-1};
				q.push(mt[b]);
			}
		}
		return false;
	}
	maxmatching(const vvc<int>&gg):g(gg),n(g.size()),sz(0),
		p(n),t(n,-1),mt(n,-1),f(n){
		rep(i,n)if(mt[i]==-1)
			sz+=arg(i);
	}
	//codechef HAMILG
	//res[i]=最大マッチングに必ず含まれるべき頂点なら 1, そうでないなら 0
	vi need(){
		rep(i,n)if(mt[i]==-1)
			arg(i);
		vi res(n);
		rep(i,n)res[i]=(mt[i]!=-1&&t[i]!=sz);
		return res;
	}
};

//VERIFY: yosupo
//KUPC2017J
//AOJDSL1A
//without rank
struct unionfind{
	vi p,s;
	int c;
	unionfind(int n):p(n,-1),s(n,1),c(n){}
	int find(int a){
		return p[a]==-1?a:(p[a]=find(p[a]));
	}
	//set b to a child of a
	bool unite(int a,int b){
		a=find(a);
		b=find(b);
		if(a==b)return false;
		p[b]=a;
		s[a]+=s[b];
		c--;
		return true;
	}
	bool same(int a,int b){
		return find(a)==find(b);
	}
	int sz(int a){
		return s[find(a)];
	}
};

void slv(){
	int n;cin>>n;
	vc<bool> used(n);
	vi rw=readvi(n,-1);
	rep(i,n)if(rw[i]!=-1)used[rw[i]]=true;
	int none=inf;
	rep(i,n)if(!used[i])none=i;
	if(none<n)used[none]=true;
	rw.insert(rw.bg,none);
	rw.pb(none);
	rw.pb(none);
	dmp(rw);
	n+=3;
	vi vs;
	rep(i,n)if(rw[i]!=-1)vs.pb(rw[i]);
	mkuni(vs);
	rep(i,n)if(rw[i]!=-1)rw[i]=lwb(vs,rw[i]);
	int s=si(vs);
	using T=tuple<int,int,int>;
	vc<T> es,fs;
	vc<pi> lrs;
	for(int i=0;i+1<n;){
		assert(rw[i]!=-1);
		int j=i+1;
		while(j<n&&rw[j]==-1)j++;
		int lf=rw[i],rt=rw[j];
		int mid=(j-i-1);
		if(mid==0){
			if(lf==rt){
				fs.eb(lf,rt,-1);
			}
		}else if(mid%2==0){
			if(lf!=rt)es.eb(lf,rt,si(lrs));
			lrs.eb(i,j);
		}else{
			if(lf==rt){
				rw[i+1]=rw[i];
				continue;
			}else{
				fs.eb(lf,rt,si(lrs));
			}
			lrs.eb(i,j);
		}
		i=j;
	}
	vi has(s);
	vi tp(si(lrs),-1);
	//even 1->matched
	//odd 0,1 use left,right
	//process fs
	unionfind uf(s);
	vi incyc(s);
	vvc<pi> g(s);
	for(auto [a,b,i]:fs){
		g[b].eb(a,(i==-1?-1:i*2));
		g[a].eb(b,(i==-1?-1:i*2+1));
		if(!uf.unite(a,b))incyc[a]=1;
	}
	vc<bool> done(s);
	auto workfs=[&](int root){
		assert(!done[root]);
		auto dfs=[&](auto self,int v)->void{
			if(done[v])return;
			done[v]=true;
			for(auto [to,i]:g[v]){
				if(i!=-1){
					if(tp[i/2]==-1){
						tp[i/2]=i%2;
						has[to]=1;
					}
				}else{
					has[to]=1;
				}
				self(self,to);
			}
		};
		dfs(dfs,root);
	};
	rep(root,s)if(!done[root]&&incyc[root]){
		workfs(root);
	}
	vvc<int> sibling(s);
	rep(i,s)sibling[uf.find(i)].pb(i);
	rep(i,s){
		if(done[i]!=has[i]){
			dmp(done);
			dmp(has);
			dmp(g);
			dmp(sibling);
			assert(false);
		}
	}
	rep(i,s)if(done[i])sibling[i].clear();
	sibling.erase(remove_if(all(sibling),[](vi a){return a.empty();}),sibling.ed);
	
	map<pi,int> buf;
	auto add=[&](int i,int j,int k){
		if((!done[i])&&(!done[j])){
			i=uf.find(i);
			j=uf.find(j);
			buf[minmax(i,j)]=k;
		}
	};
	for(auto [a,b,c]:es)add(a,b,c);
	dmp(es);
	dmp(vs);
	dmp(sibling);
	vvc<int> h(s);
	for(auto [ij,k]:buf){
		auto [i,j]=ij;
		dmp2(i,j);
		h[i].pb(j);
		h[j].pb(i);
	}
	maxmatching mt(h);
	dmp(mt.mt);
	/*rep(i,s)if(i<mt.mt[i]){
		if(mt.mt[i]<s){
			tp[buf[pi(i,mt.mt[i])]]=1;
			if(!done[i])workfs(i);
		}else{
		}
	}*/
	for(auto [ij,k]:buf){
		auto [i,j]=ij;
		int x=uf.find(i);
		int y=uf.find(j);
		if(x>y)swap(x,y);
		if(mt.mt[x]==y){
			tp[k]=1;
			workfs(i);
			workfs(j);
		}
	}
	rep(i,s)if(!done[i])workfs(i);
	dmp(rw);
	dmp(vs);
	vi a=rw;
	rep(i,n)if(a[i]!=-1)a[i]=vs[a[i]];
	int head=0;
	rep(i,si(lrs)){
		auto [l,r]=lrs[i];
		l++;
		if((r-l)%2==0){
			if(tp[i]<=0){
				//do nothing
			}else{
				a[l]=a[l-1];
				a[r-1]=a[r];
				l++;
				r--;
			}
		}else{
			assert(tp[i]==0||tp[i]==1);
			if(tp[i]==0){
				a[l]=a[l-1];
				l++;
			}else{
				a[r-1]=a[r];
				r--;
			}
		}
		for(int j=l;j<r;j+=2){
			while(head<n&&used[head])head++;
			assert(head<n);
			a[j]=a[j+1]=head;
			used[head]=true;
		}
	}
	dmp(a);
	a.erase(a.bg);
	a.pop_back();
	a.pop_back();
	n-=3;
	dmp(a);
	assert(*min_element(all(a))>=0);
	assert(*max_element(all(a))<n);
	print_offset(a,1);
}

signed main(){
	cin.tie(0);
	ios::sync_with_stdio(0);
	cout<<fixed<<setprecision(20);
	
	//int t;cin>>t;rep(_,t)
	slv();
}
