按操作顺序用转置、切片和行逆序模拟图像旋转与翻转。
OJ: noi_openjudge
题目 ID: ch0112-09
难度:普及-
标签:矩阵模拟python
日期: 2026-07-30 23:01
题意
对灰度矩阵依次执行顺时针旋转、逆时针旋转、左右翻转或上下翻转,输出最终图像。
思路
顺时针旋转可写为“先逆序行,再转置”:zip(*image[::-1])。逆时针旋转为先转置再逆序行。左右翻转是每行 [::-1],上下翻转是行列表 [::-1]。操作必须按给定字符串顺序执行。
代码
Python代码
python
row_count, column_count = map(int, input().split())
image = [input().split() for _ in range(row_count)]
operations = input()
for operation in operations:
if operation == "A":
image = [list(row) for row in zip(*image[::-1])]
elif operation == "B":
image = [list(row) for row in zip(*image)][::-1]
elif operation == "C":
image = [row[::-1] for row in image]
else:
image = image[::-1]
for row in image:
print(*row)C++代码
cpp
#include <cstdio>
#include <cstring>
int map[200][200];
int map_bak[200][200];
char str[1000];
int m,n;
void _swap(int &a,int &b){
int t = a; a = b; b = t;
}
void clock(){
int i,j;
for(i=1;i<=m;i++)
for(j=1;j<=n;j++){
map_bak[j][m-i+1]= map[i][j];
}
memcpy(map,map_bak,sizeof(map));
_swap(n,m);
}
void anti_clock(){
int i,j;
for(i=1;i<=m;i++)
for(j=1;j<=n;j++){
map_bak[n-j+1][i]= map[i][j];
}
memcpy(map,map_bak,sizeof(map));
_swap(n,m);
}
void left_right(){
int i,j;
for (i=1;i<=m;i++){
for (j=1;j<=n;j++){
map_bak[i][n-j+1]= map[i][j];
}
}
memcpy(map,map_bak,sizeof(map));
}
void up_down(){
int i,j;
for (i=1;i<=m;i++){
for (j=1;j<=n;j++){
map_bak[m-i+1][j]= map[i][j];
}
}
memcpy(map,map_bak,sizeof(map));
}
int main(){
scanf("%d%d",&m,&n);
int i,j;
for (i=1;i<=m;i++){
for (j=1;j<=n;j++){
scanf("%d",&map[i][j]);
}
}
scanf("%s",str);
int len = strlen(str);
for (i=0;i<len;i++){
char c = str[i];
if( c == 'A')
clock();
else if( c == 'B')
anti_clock();
else if( c == 'C')
left_right();
else if( c == 'D')
up_down();
}
for (i=1;i<=m;i++){
for (j=1;j<=n;j++){
printf("%d ",map[i][j]);
}
printf("\n");
}
return 0;
}复杂度
设操作数为
总结
矩阵变换的关键是每一步都使用当前矩阵,旋转后行列数会交换。