/*
Author of all code: Pedro BIGMAN Dias
Last edit: 15/02/2021
*/
#include <iostream>
#include <vector>
#include <cmath>
#include <algorithm>
#include <string>
#include <map>
#include <unordered_map>
#include <set>
#include <unordered_set>
#include <queue>
#include <deque>
#include <list>
#include <iomanip>
#include <stdlib.h>
#include <time.h>
#include <cstring>
using namespace std;
typedef int ll;
typedef unsigned long long int ull;
typedef long double ld;
#define REP(i,a,b) for(ll i=(ll) a; i<(ll) b; i++)
#define pb push_back
#define mp make_pair
#define pl pair<ll,ll>
#define ff first
#define ss second
#define whole(x) x.begin(),x.end()
#define DEBUG(i) cout<<"Pedro Is The Master "<<i<<endl
#define INF 500000000LL
#define EPS 0.00000001
#define pi 3.14159
ll mod=1000000007LL;

template<class A=ll> 
void Out(vector<A> a) {REP(i,0,a.size()) {cout<<a[i]<<" ";} cout<<endl;}

template<class A=ll>
void In(vector<A> &a, ll N) {A cur; REP(i,0,N) {cin>>cur; a.pb(cur);}} 

ll N; vector<pl> p; ll ans;
vector<ll> pos; 
vector<bool> active; 
ll maxpref; ll maxsuffix;
ll maxvalue; ll minvalue;
ll used;
bool ok;
ll curplaced; ll curans;
vector<ll> a,b; ll l,r;

ll other(ll s)
{
	ll ind=pos[s]; if(p[ind].ff==s) {return p[ind].ss;} else {return p[ind].ff;}
}

bool IsUp(ll s)
{
	ll ind=pos[s];
	if(p[ind].ff==s) {return true;}
	else {return false;}
}

void Use(ll s, ll place)
{
	if(!active[s]) {ok=false; return;}
	bool up=false;
	if(place==1) {up=true;maxvalue=max(maxvalue,s); minvalue=min(minvalue,other(s)); a[l]=s; b[l]=other(s); l++;} //P1
	if(place==2) {up=true;minvalue=min(s,minvalue); maxvalue=max(maxvalue,other(s)); a[r]=s; b[r]=other(s); r--;} //S1
	if(place==3) {minvalue=min(s,minvalue); maxvalue=max(maxvalue,other(s)); a[l]=other(s); b[l]=s; l++;} //P2
	if(place==4) {maxvalue=max(s,maxvalue);  minvalue=min(minvalue,other(s)); a[r]=other(s); b[r]=s; r--;} //S2
	used++; curplaced++;
	active[s]=false; active[other(s)]=false;
	if(IsUp(s) != up) {swap(p[pos[s]].ff,p[pos[s]].ss); curans++;} 
	ll cur = maxpref+1; while(cur<2*N && !active[cur]) {maxpref=cur; cur++;} 
	cur = maxsuffix-1;  while(cur>=0 && !active[cur]) {maxsuffix=cur; cur--;} 
	
}

int main()
{
    ios_base::sync_with_stdio(0);
    cin.tie(0); cout.tie(0);
	ok=true;
    cin>>N; pl cur; REP(i,0,N) {cin>>cur.ff>>cur.ss; cur.ff--; cur.ss--; p.pb(cur);}
	REP(i,0,2*N) {pos.pb(-1);}
	REP(i,0,N) {pos[p[i].ff]=i; pos[p[i].ss]=i;}
	maxpref=0LL; maxsuffix=2*N;
	maxvalue=0LL; minvalue=2*N;
	used=0LL; ans=0LL;
	bool flip=false; if(p[pos[0]].ff!=0) {flip=true;} 
	if(flip) {REP(i,0,N) {swap(p[i].ff,p[i].ss);}}
	REP(i,0,2*N) {active.pb(true);}
	curplaced=0; curans=0; 
	l=0; r=N-1;
	REP(i,0,N) {a.pb(-1); b.pb(-1);}
	Use(0,1);
	while(used<N)
	{
		if(maxvalue>maxpref)
		{
			bool up = IsUp(maxvalue);
			if(up) {Use(maxpref+1,4);} else {Use(maxpref+1,1);}
			if(!ok) {cout<<-1<<endl; return 0;}
			continue;
		}
		else if(minvalue<maxsuffix)
		{
			bool up = IsUp(minvalue);
			if(up) {Use(maxsuffix-1,3);} else {Use(maxsuffix-1,2);}
			if(!ok) {cout<<-1<<endl; return 0;}
			continue;
		}
		ans+=min(curans,curplaced-curans);
		curplaced=0; curans=0;
		Use(maxpref+1,1);
		if(!ok) {cout<<-1<<endl; return 0;}
	}
	ans+=min(curans,curplaced-curans);
	REP(i,0,N-1) 
	{
		if(a[i+1]<a[i] || b[i+1]>b[i]) {cout<<-1<<endl; return 0;}
	}
	cout<<ans<<endl;
    return 0;
}