#include <iostream>
#include <sstream>
#include <fstream>
#include <string>
#include <vector>
#include <deque>
#include <queue>
#include <stack>
#include <set>
#include <map>
#include <algorithm>
#include <functional>
#include <utility>
#include <bitset>
#include <cmath>
#include <cstdlib>
#include <ctime>
#include <cstdio>

using namespace std;

#define REP(i,n) for((i)=0;(i)<(int)(n);(i)++)
#define snuke(c,itr) for(__typeof((c).begin()) itr=(c).begin();itr!=(c).end();itr++)

int N;
int a[60];
int f[60][60];

class MultiplicationTable{
	public:
	
	vector <int> getMultiplicationTable(vector <int> g){
		int i,j,k;
		
		N = g.size();
		REP(i,N) a[i] = -1;
		
		int x = 0;
		for(i=1;;i++){
			if(a[x] != -1) break;
			a[x] = i;
			x = g[x];
		}
		
		REP(i,N+10) REP(j,N) if(a[j] == -1 && a[g[j]] != -1) a[j] = a[g[j]] - 1;
		
		REP(i,N){
			if(a[i] == -1){
				REP(j,N) f[i][j] = i;
			} else {
				REP(j,N){
					int tmp = j;
					REP(k,a[i]) tmp = g[tmp];
					f[i][j] = tmp;
				}
			}
		}
		
		bool good = true;
		REP(i,N) REP(j,N) REP(k,N) if(f[f[i][j]][k] != f[i][f[j][k]]) good = false;
		
		vector <int> ans;
		if(good){
			REP(i,N) REP(j,N) ans.push_back(f[i][j]);
		} else {
			ans.push_back(-1);
		}
		
		return ans;
	}

};
