#include<cstdio>
#include<cstdlib>
#include<algorithm>
using namespace std;
typedef pair<int,int> abcd;
inline char nc(){
static char buf[100000],*p1=buf,*p2=buf;
if (p1==p2) { p2=(p1=buf)+fread(buf,1,100000,stdin); if (p1==p2) return EOF; }
return *p1++;
}
inline void read(int &x){
char c=nc(),b=1;
for (;!(c>='0' && c<='9');c=nc()) if (c=='-') b=-1;
for (x=0;c>='0' && c<='9';x=x*10+c-'0',c=nc()); x*=b;
}
const int N=805;
struct edge{
int u,v;
int next;
}G[N*N];
int head[N],inum;
inline void add(int u,int v,int p){
G[p].u=u; G[p].v=v; G[p].next=head[u]; head[u]=p;
}
int vst[N*N];
int lst[N],pnt;
#define V G[p].v
inline void dfs(int u){
for (int p=head[u];p;p=G[p].next)
if (!vst[p]){
vst[p]=1;
dfs(V);
lst[++pnt]=p;
}
}
int n,m;
int cot[N][N];
int pos[405][405][405];
abcd ans[N*N]; int tot;
int main(){
int a;
freopen("t.in","r",stdin);
freopen("t.out","w",stdout);
read(n); read(m);
for (int i=1;i<=n;i++)
for (int j=1;j<=m;j++)
read(a),cot[i][a]++,pos[i][a][++*pos[i][a]]=(i-1)*m+j;
for (int i=1;i<=n;i++)
for (int j=1;j<=m;j++){
for (int k=2;k<=cot[i][j];k++)
add(i,j+n,++inum);
if (cot[i][j]<1)
add(j+n,i,++inum);
}
for (int i=n+1;i<=n+m;i++){
pnt=0;
dfs(i);
if (pnt){
int last=n*m+1;
for (int i=1;i<=pnt;i++)
if (G[lst[i]].u<=n){
int u=G[lst[i]].u,v=G[lst[i]].v-n;
ans[++tot].first=pos[u][v][(*pos[u][v])--]; ans[tot].second=last;
last=ans[tot].first;
}
ans[++tot].first=n*m+1; ans[tot].second=last;
}
}
printf("%d\n",tot);
for (int i=1;i<=tot;i++)
printf("%d %d\n",ans[i].first,ans[i].second);
return 0;
}