我知道如何转置矩阵,但是如何转置具有奇数行反转形式的矩阵。
示例3 * 3矩阵
输出
答案 0 :(得分:1)
这是一个将问题分解为更小的子问题的解决方案。函数reverse_row()
是一个反转数组的函数,函数transpose_array()
将数组转换到位。
第一个函数reverse_row()
在具有奇数索引的2d数组的行中循环调用,然后在结果数组上调用transpose_array()
函数。请注意,测试if (i % 2) {}
用于确定数组索引是奇数还是偶数,因为i % 2
仅在0
为偶数时才计算为i
;您还可以避免此测试,只需在每次迭代(从1开始)将i
增加2,如评论中@Lưu Vĩnh Phúc所示:
for (size_t i = 1; i < MATRIX_SZ; i += 2) {
reverse_row(MATRIX_SZ, array[i]);
}
另请注意,要将方形矩阵转置到位,您不需要遍历所有元素,而只需迭代对角线上方或下方的元素,并使用适当的元素进行交换。在这种情况下,我选择迭代对角线下方的元素,与对角线上方的相应元素进行交换。当然,对角线上的元素保持不变,因此根本不会迭代。
这是代码,使用4X4数组作为输入。此代码适用于方形矩阵,可以适用于矩形矩阵。这需要谨慎选择用于表示矩阵的数组大小或动态分配。
#include <stdio.h>
#define MATRIX_SZ 4
void print_array(size_t n, int arr[n][n]);
void reverse_row(size_t n, int arr[n]);
void transpose_array(size_t n, int arr[n][n]);
int main(void)
{
int array[MATRIX_SZ][MATRIX_SZ] = { { 1, 2, 3, 4 },
{ 5, 6, 7, 8 },
{ 9, 10, 11, 12 },
{ 13, 14, 15, 16 } };
puts("Before transformation:");
print_array(MATRIX_SZ, array);
putchar('\n');
for (size_t i = 0; i < MATRIX_SZ; i++) {
if (i % 2) {
reverse_row(MATRIX_SZ, array[i]);
}
}
transpose_array(MATRIX_SZ, array);
puts("After transformation:");
print_array(MATRIX_SZ, array);
putchar('\n');
return 0;
}
void print_array(size_t n, int arr[n][n])
{
for (size_t i = 0; i < n; i++) {
for (size_t j = 0; j < n; j++) {
printf("%5d", arr[i][j]);
}
putchar('\n');
}
}
void reverse_row(size_t n, int arr[n])
{
size_t mid = n / 2;
for (size_t i = 0; i < mid; i++) {
size_t swap_dx = n - 1 - i;
int temp = arr[i];
arr[i] = arr[swap_dx];
arr[swap_dx] = temp;
}
}
void transpose_array(size_t n, int arr[n][n])
{
for (size_t i = 0; i < n; i++) {
for (size_t j = 0; j < i; j++) {
int temp = arr[i][j];
arr[i][j] = arr[j][i];
arr[j][i] = temp;
}
}
}
以下是程序输出:
Before transformation:
1 2 3 4
5 6 7 8
9 10 11 12
13 14 15 16
After transformation:
1 8 9 16
2 7 10 15
3 6 11 14
4 5 12 13
答案 1 :(得分:0)
如果我已正确理解作业,则程序可以按以下方式查看。
#include <stdio.h>
#define MAX_VALUE 100
int main(void)
{
while ( 1 )
{
printf( "Enter the size of an array (0 - Exit): " );
size_t n;
if ( scanf( "%zu", &n ) != 1 || n == 0 ) break;
putchar('\n');
n %= MAX_VALUE;
int a[n][n];
for ( size_t i = 0; i < n; i++ )
{
for ( size_t j = 0; j < n; j++ )
{
a[i][j] = n * i + j;
}
}
for (size_t i = 0; i < n; i++)
{
for (size_t j = 0; j < n; j++)
{
printf("%3d ", a[i][j]);
}
putchar('\n');
}
putchar('\n');
for (size_t i = 0; i < n; i++)
{
for (size_t j = i; j < n; j++)
{
if (j % 2 == 1 && i < n / 2)
{
int tmp = a[j][i];
a[j][i] = a[j][n - i - 1];
a[j][n - i - 1] = tmp;
}
if (i != j)
{
int tmp = a[i][j];
a[i][j] = a[j][i];
a[j][i] = tmp;
}
}
}
for (size_t i = 0; i < n; i++)
{
for (size_t j = 0; j < n; j++)
{
printf("%3d ", a[i][j]);
}
putchar('\n');
}
putchar('\n');
}
return 0;
}
它的输出可能看起来像
Enter the size of an array (0 - Exit): 10
0 1 2 3 4 5 6 7 8 9
10 11 12 13 14 15 16 17 18 19
20 21 22 23 24 25 26 27 28 29
30 31 32 33 34 35 36 37 38 39
40 41 42 43 44 45 46 47 48 49
50 51 52 53 54 55 56 57 58 59
60 61 62 63 64 65 66 67 68 69
70 71 72 73 74 75 76 77 78 79
80 81 82 83 84 85 86 87 88 89
90 91 92 93 94 95 96 97 98 99
0 19 20 39 40 59 60 79 80 99
1 18 21 38 41 58 61 78 81 98
2 12 22 37 42 57 62 77 82 97
3 13 23 36 43 56 63 76 83 96
4 14 24 34 44 55 64 75 84 95
5 15 25 35 45 54 65 74 85 94
6 16 26 33 46 53 66 73 86 93
7 17 27 32 47 52 67 72 87 92
8 11 28 31 48 51 68 71 88 91
9 10 29 30 49 50 69 70 89 90
Enter the size of an array (0 - Exit): 3
0 1 2
3 4 5
6 7 8
0 5 6
1 4 7
2 3 8
Enter the size of an array (0 - Exit): 0
编译器应该支持可变长度数组。否则,您可以为具有固定大小的数组重写程序。