#define _USE_MATH_DEFINES
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <string.h>
#include <string>
#include <vector>
#include <algorithm>
#include <map>
#include <queue>
#include <set>
#include <iostream>
#include <fstream>
#include <chrono>

using namespace std;

void solve(int test, std::istream &in) {
    int n;
    in >> n;
    vector<int> a(n), b(n), p(n);
    for (int i = 0; i < n; i++)
        in >> a[i];
    for (int i = 0; i < n; i++)
        in >> b[i];
    for (int i = 0; i < n; i++) {
        in >> p[i];
        p[i]--;
    }
    vector<vector<int>> s;
    for (int i = 0; i < n; i++) {
        if (p[i] >= 0) {
            s.push_back(vector<int>());
            int i2 = i;
            while (p[i2] >= 0) {
                s.back().push_back(i2);
                int tmp = p[i2];
                p[i2] = -1;
                i2 = tmp;
            }
        }
    }
    int m = 0;
    for (int i = 0; i < s.size(); i++) {
        if (s[i].size() == 1)
            continue;
        for (int j = 0; j < s[i].size(); j++) {
            int u = s[i][j];
            int v = j == s[i].size() - 1 ? s[i][0] : s[i][j + 1];
            if (a[u] <= b[v]) {
                m = -1;
                break;
            }
        }
        if (m < 0)
            break;
        m += s[i].size() - 1;
    }
    printf("%d\n", m);
    if (m > 0) {
        for (int i = 0; i < s.size(); i++) {
            if (s[i].size() == 1)
                continue;
            int max = 0, arg = -1;
            for (int j = 0; j < s[i].size(); j++) {
                int u = s[i][j];
                if (a[u] > max) {
                    max = a[u];
                    arg = j;
                }
            }
            int j = arg == s[i].size() - 1 ? 0 : arg + 1;
            while (j != arg) {
                printf("%d %d\n", s[i][arg] + 1, s[i][j] + 1);
                j++;
                if (j == s[i].size())
                    j = 0;
            }
        }
    }
}

int main(int argc, char *argv[]) {
#ifdef VLAD_LOCAL
    ifstream in("in.txt");
    auto start = std::chrono::steady_clock::now();
#else
    istream &in = cin;
#endif
    solve(0, in);
#ifdef VLAD_LOCAL
    auto end = std::chrono::steady_clock::now();
    double seconds = (double)std::chrono::duration_cast<std::chrono::milliseconds>(end - start).count() / 1000;
    printf("%.3lf seconds\n", seconds);
#endif
	return 0;
}

/* これを翻訳している間、あなたはあなたの人生のいくつかの貴重な瞬間を無駄にしました */

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

#define IOS ios_base::sync_with_stdio(false);cin.tie(0);cout.tie(0);
#define ll long long
#define pb push_back
#define fi first
#define se second
#define all(x) (x).begin(),(x).end()
#define S(x) (int)(x).size()
#define L(x) (int)(x).length()
#define ld long double
#define mem(x,y) memset(x,y,sizeof x)

#include<ext/pb_ds/assoc_container.hpp>
#include<ext/pb_ds/tree_policy.hpp>
using namespace __gnu_pbds;
typedef tree<int , null_type , less<int> , rb_tree_tag , tree_order_statistics_node_update> ordered_set;

const int mod = 1e9+7;
const ll infl = 0x3f3f3f3f3f3f3f3fLL;
const int infi = 0x3f3f3f3f;

vector<array<int,2>> adj[250009];
int a[250009],b[250009];
int r,c;
int d[250009];

int state(int i, int j)
{
	return i*c+j;
}

int main()
{
	IOS
	cin>>r>>c;
	for(int i=0;i<r;i++)
	for(int j=0;j<c-1;j++)
	cin>>a[i*c+j];
	
	for(int i=0;i<r-1;i++)
	for(int j=0;j<c;j++)
	cin>>b[i*c+j];
	
	for(int i=0;i<r;i++)
	for(int j=0;j<c;j++)
	{
		if(j+1<c) adj[state(i,j)].pb({state(i,j+1),a[state(i,j)]});
		if(j-1>=0) adj[state(i,j)].pb({state(i,j-1),a[state(i,j-1)]});
		if(i+1<r) adj[state(i,j)].pb({state(i+1,j),b[state(i,j)]});
		for(int k=0;k<i;k++)
		adj[state(i,j)].pb({state(k,j),i-k+1});
	}
	
	int s=0;
	mem(d,infi);
	d[0] = 0;
	set<pair<int, int>> q;
	q.insert({0, s});
    while (!q.empty()) {
        int v = q.begin()->second;
        q.erase(q.begin());

        for (auto edge : adj[v]) {
            int to = edge[0];
            int len = edge[1];

            if (d[v] + len < d[to]) {
                q.erase({d[to], to});
                d[to] = d[v] + len;
                q.insert({d[to], to});
            }
        }
    }
    cout<<d[r*c-1]<<'\n';
}
