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

#define INF_LL (int64)1e18
#define INF (int32)1e9
#define REP(i, n) for(int64 i = 0;i < (n);i++)
#define FOR(i, a, b) for(int64 i = (a);i < (b);i++)
#define all(x) x.begin(),x.end()
#define fs first
#define sc second

using int32 = int_fast32_t;
using uint32 = uint_fast32_t;
using int64 = int_fast64_t;
using uint64 = uint_fast64_t;
using PII = pair<int32, int32>;
using PLL = pair<int64, int64>;

const double eps = 1e-10;

template<typename A, typename B>inline void chmin(A &a, B b){if(a > b) a = b;}
template<typename A, typename B>inline void chmax(A &a, B b){if(a < b) a = b;}

template<typename T>
vector<T> make_v(size_t a){return vector<T>(a);}

template<typename T,typename... Ts>
auto make_v(size_t a,Ts... ts){
  return vector<decltype(make_v<T>(ts...))>(a,make_v<T>(ts...));
}

template<typename T,typename U,typename... V>
typename enable_if<is_same<T, U>::value!=0>::type
fill_v(U &u,const V... v){u=U(v...);}

template<typename T,typename U,typename... V>
typename enable_if<is_same<T, U>::value==0>::type
fill_v(U &u,const V... v){
  for(auto &e:u) fill_v<T>(e,v...);
}

struct BiMatch{
    int L,R;
    vector<vector<int> > G;
    vector<int> match,level;

    BiMatch(){}
    BiMatch(int L,int R):L(L),R(R),G(L+R),match(L+R,-1),level(L+R){}

    void add_edge(int u,int v){
        G[u].emplace_back(v+L);
        G[v+L].emplace_back(u);
    }

    bool bfs(){
        fill(level.begin(),level.end(),-1);
        queue<int> q;
        for(int i=0;i<L;i++){
            if(match[i]<0){
                level[i]=0;
                q.emplace(i);
            }
        }
        bool found=false;
        while(!q.empty()){
            int v=q.front();q.pop();
            for(int u:G[v]){
                if(~level[u]) continue;
                level[u]=level[v]+1;
                int w=match[u];
                if(w==-1){
                    found=true;
                    continue;
                }
                if(~level[w]) continue;
                level[w]=level[u]+1;
                q.emplace(w);
            }
        }
        return found;
    }

    bool dfs(int v){
        for(int u:G[v]){
            if(level[v]+1!=level[u]) continue;
            level[u]=-1;
            int w=match[u];
            if(w<0||dfs(w)){
                match[v]=u;
                match[u]=v;
                level[v]=-1;
                return true;
            }
        }
        level[v]=-1;
        return false;
    }

    int build(){
        int res=0;
        while(bfs())
            for(int i=0;i<L;i++)
                if(match[i]<0&&dfs(i))
                    res++;
        return res;
    }

};

int main(void){
	cin.tie(0);
	ios::sync_with_stdio(false);
	int64 N, M;
	cin >> N >> M;
	auto A = make_v<int64>(N, M);
	vector<int64> row(N*M);
	vector<int32> used(N*M, 0);
	REP(i, N) {
	    REP(j, M) {
	        cin >> A[i][j]; A[i][j]--;
	        row[A[i][j]] = i;
	    }
	}
	auto B = make_v<int64>(N, M);
	REP(i, M) {
        BiMatch bm(N, N);
        REP(j, N*M) {
            if (!used[j]) {
                bm.add_edge(row[j], j/M);
            }
        }
        bm.build();
        REP(j, N) {
            REP(k, M) {
                if (bm.match[j]-N == A[j][k]/M && !used[A[j][k]]) {
                    used[A[j][k]] = 1;
                    B[j][i] = A[j][k]+1;
                    break;
                }
            }
        }
	}
	REP(i, N) {
	    REP(j, M) {
	        cout << B[i][j] << " ";
	    }
	    cout << endl;
	}
	REP(i, N) {
	    REP(j, M) {
	        REP(k, N) {
	            if ((B[k][j]-1)/M == i) {
	                cout << B[k][j] << " ";
	                break;
	            }
	        }
	    }
	    cout << endl;
	}
}


Measured memory_bytes: 768