C++で2次元マトリックスに同心の長方形パターンを出力する方法
はじめに
この記事では、2次元マトリックス内にお互いが同心(同じ中心を持つ)になるように長方形パターンを出力する方法を解説します。
まず、具体例を見ながら問題を理解しましょう。
n = 4 の場合 : 4 4 4 4 4 4 4 4 3 3 3 3 3 4 4 3 2 2 2 3 4 4 3 2 1 2 3 4 4 3 2 2 2 3 4 4 3 3 3 3 3 4 4 4 4 4 4 4 4
このように、整数値 n を入力として受け取り、外側から内側へと値が1ずつ減少していく同心の長方形パターンを出力します。一般化すると次のような形になります。
n n n n n n n-1 n-1 n-1 n n n-1 n-2 n-1 n n n-1 n-1 n-1 n n n n n n
パターンの構造
この問題において、2次元マトリックスは全部で (2n-1) 行 × (2n-1) 列のサイズになります。このマトリックスは大きく2つの部分に分けて出力します。
- 上半分: 0 行目から (2n-1)/2 行目まで
- 下半分: (2n-1)/2 + 1 行目から 2n-2 行目まで
各行では、値が行番号 i に達するまで1ずつ減少していき、中心に到達した後は再び n まで増加していきます。つまり、左端から中央までは「n → n-i」へと減少し、中央から右端までは逆に「n-i → n」へと増加する、左右対称の美しい構造になっています。
C++での実装例
上記のロジックをもとに、この問題を解くプログラムを作成してみましょう。
#include <bits/stdc++.h>
using namespace std;
// 同心の長方形パターンを出力する関数
void print2Dsequence(int n){
int s = 2 * n - 1;
// 上半分(中央行を含む)の出力
for (int i = 0; i < (s / 2) + 1; i++) {
int m = n;
// 左側:値を減少させながら出力
for (int j = 0; j < i; j++) {
cout << m << " ";
m--;
}
// 中央部分:同じ値を繰り返し出力
for (int k = 0; k < s - 2 * i; k++) {
cout << n - i << " ";
}
// 右側:値を増加させながら出力
m = n - i + 1;
for (int l = 0; l < i; l++) {
cout << m << " ";
m++;
}
cout << endl;
}
// 下半分の出力(上半分を逆順に表示)
for (int i = s / 2 - 1; i >= 0; i--) {
int m = n;
for (int j = 0; j < i; j++) {
cout << m << " ";
m--;
}
for (int k = 0; k < s - 2 * i; k++) {
cout << n - i << " ";
}
m = n - i + 1;
for (int l = 0; l < i; l++) {
cout << m << " ";
m++;
}
cout << endl;
}
}
int main(){
int n = 4;
cout << "The sequence of concentric rectangles of 4 is : \n";
print2Dsequence(n);
return 0;
}
出力結果
n = 4 の場合の同心長方形パターンの出力は以下の通りです。
4 4 4 4 4 4 4 4 3 3 3 3 3 4 4 3 2 2 2 3 4 4 3 2 1 2 3 4 4 3 2 2 2 3 4 4 3 3 3 3 3 4 4 4 4 4 4 4 4
まとめ
このプログラムの計算量は O((2n-1)2)、すなわち O(n2) であり、各要素を一度ずつ出力するため効率的な実装となっています。マトリックスを上下半分に分割し、行ごとの「減少 → 一定 → 増加」という対称性を利用することで、シンプルかつ明快に同心の長方形パターンを実現できます。
-
Cプログラムで行列を対角パターンに沿って数値出力する方法
この課題は、n×nの行列を対角パターンで出力することです。 例えば n が 3 の場合、対角パターンに従って行列を出力すると、次のような配置になります。 そして、実際の出力結果は以下の通りです。 実行例 Input: 3 Output: 1 2 4 3 5 7 6 8 9 Input: 4 Output: 1 2 4 7 3 5 8 11 6 9 12 14 10 13 15 16 考え方 一見すると、「数値 n を受け取り n×n の行列を生成し、それを対角方向に走査しながら別の行列へ値を格納する」というアプローチが思い浮かびます
-
C++で2次元行列を反時計回りのスパイラル形式で出力する方法
この記事では、2次元行列が与えられたときに、そのすべての要素を反時計回りのスパイラル形式で出力する方法を解説します。 反時計回りのスパイラル形式とは? 反時計回りのスパイラル形式とは、行列の左上の要素から開始し、最初に下方向へ進み、続いて右→上→左と方向を変えながら、渦巻き状に外側から内側へと要素をたどっていく走査方法です。 例として、次の4×4の行列を見てみましょう。 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 この行列を反時計回りに走査すると、出力は「1 5 9 13 14 15 16 12 8 4 3 2 6 10