Here's my solution:
#include "stdafx.h"
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
#include <math.h>
#include <time.h>
#define N 10
#define DIST_N 10
typedef struct tagDists
{
int** dist;
int size_x;
int size_y;
bool is_d;
} DISTS, *LP_DISTS;
int main()
{
int** matrix = (int**)malloc(sizeof(int*) * N);
memset((void*)matrix, 0x00, sizeof(int*) * N);
srand((unsigned)time(nullptr));
for (int i = 0; i < N; i++)
{
matrix[i] = (int*)malloc(sizeof(int) * N);
memset((void*)matrix[i], 0x00, sizeof(int) * N);
for (int j = 0; j < N; j++)
{
matrix[i][j] = rand() % 9 + 1;
printf("%d ", matrix[i][j]);
}
printf("\n");
}
printf("\n");
int dist_size = (int)pow((double)N, 2) / DIST_N;
int dist_size_x = int(sqrt((double)dist_size));
int dist_size_y = dist_size / dist_size_x;
int n_chunks_row = int(ceil(N / (double)dist_size_x));
int n_chunks_col = int(ceil(N / (double)dist_size_y));
int n_dists = n_chunks_row * n_chunks_col;
LP_DISTS dists = (LP_DISTS)malloc(sizeof(DISTS) * n_dists);
memset((void*)dists, 0x00, sizeof(DISTS) * n_dists);
int n = 0;
for (int t1 = 0; t1 < n_chunks_row; t1++)
{
int start_x = t1 * dist_size_x;
int end_x = (t1 + 1) * dist_size_x;
start_x = (start_x > N) ? N : start_x;
end_x = (end_x > N) ? N : end_x;
for (int t2 = 0; t2 < n_chunks_col; t2++)
{
int start_y = t2 * dist_size_y;
int end_y = (t2 + 1) * dist_size_y;
start_y = (start_y > N) ? N : start_y;
end_y = (end_y > N) ? N : end_y;
dists[n].dist = (int**)malloc(sizeof(int*) * abs(start_x - end_x));
int n_i = 0;
for (int i = start_x; i < end_x; i++, n_i++)
{
dists[n].dist[n_i] = (int*)malloc(sizeof(int) * abs(start_y - end_y));
int n_j = 0;
for (int j = start_y; j < end_y; j++, n_j++)
dists[n].dist[n_i][n_j] = matrix[i][j];
}
dists[n].is_d = false;
dists[n].size_x = abs(start_x - end_x);
dists[n].size_y = abs(start_y - end_y);
n++;
}
}
for (int t = 0; t < n_dists; t++)
{
if ((dists[t].size_x < dist_size_x) ||
(dists[t].size_y < dist_size_y))
{
int n_items = dists[t].size_x * dists[t].size_y;
int items_per_dist = int(ceil(n_items / ((double)dist_size_x * dist_size_y)));
int* v = (int*)malloc(sizeof(int) * dists[t].size_x * dists[t].size_y);
memset((void*)v, 0x00, sizeof(int) * dists[t].size_x * dists[t].size_y);
int n = 0;
for (int s1 = 0; s1 < dists[t].size_x; s1++)
for (int s2 = 0; s2 < dists[t].size_y; s2++)
v[n++] = dists[t].dist[s1][s2];
for (int i = 0, n = 0; i < n_dists && n_items > 0; i++)
{
if ((dists[i].size_x >= dist_size_x) &&
(dists[i].size_y >= dist_size_y) && i != t)
{
if (dists[i].size_x * dists[i].size_y < dist_size)
{
dists[t].is_d = true;
int rows = int(ceil(items_per_dist / (double)N));
dists[i].dist = (int**)realloc(dists[i].dist, sizeof(int) * rows * dists[i].size_y);
dists[i].size_x += rows;
int i2 = dists[t].size_x;
for (int i1 = dists[i].size_x - rows; i1 < dists[i].size_x && --i2 >= 0; i1++)
{
int j2 = dists[t].size_y;
dists[i].dist[i1] = (int*)malloc(sizeof(int) * dists[i].size_y);
memset((void*)dists[i].dist[i1], 0x00, sizeof(int) * dists[i].size_y);
for (int j1 = 0; j1 < dists[i].size_y && --j2 >= 0; j1++)
{
dists[i].dist[i1][j1] = v[n++]; n_items--;
}
}
}
}
}
}
}
int* v = (int*)malloc(sizeof(int) * dist_size);
memset((void*)v, 0x00, sizeof(int) * dist_size);
int r = 0;
for (int t = 0; t < n_dists; t++)
{
if ((dists[t].size_x < dist_size_x) ||
(dists[t].size_y < dist_size_y))
{
if (dists[t].is_d == false)
{
for (int i = 0; i < dists[t].size_x && i < N; i++)
for (int j = 0; j < dists[t].size_y && j < N; j++)
v[r++] = dists[t].dist[i][j];
}
}
}
int** dist = (int**)malloc(sizeof(int*) * dist_size_x + 1);
memset((void*)dist, 0x00, sizeof(int*) * dist_size_x + 1);
for (int i = 0, r = 0; i < dist_size_x; i++)
{
dist[i] = (int*)malloc(sizeof(int) * dist_size_y);
memset((void*)dist[i], 0x00, sizeof(int) * dist_size_y);
for (int j = 0; j < dist_size_y; j++)
dist[i][j] = v[r++];
}
dist[dist_size_x] = (int*)malloc(sizeof(int) * dist_size_y);
memset((void*)dist[dist_size_x], 0x00, sizeof(int) * dist_size_y);
dist[dist_size_x][0] = v[r - 1];
int x = 0;
for (int t = 0; t < n_dists; t++)
{
if ((dists[t].size_x >= dist_size_x) &&
(dists[t].size_y >= dist_size_y))
{
if (dists[t].is_d == false)
{
printf("District: %d\n", x + 1);
for (int i = 0; i < dists[t].size_x && i < N; i++)
{
for (int j = 0; j < dists[t].size_y && j < N; j++)
printf("%d ", dists[t].dist[i][j]);
printf("\n");
}
printf("\n");
x++;
}
}
}
printf("District: %d\n", x + 1);
for (int i = 0; i < dist_size_x + 1; i++)
{
for (int j = 0; j < dist_size_y; j++)
printf("%d ", dist[i][j]);
printf("\n");
}
printf("\n");
return 0;
}