
No.4ベストアンサー
- 回答日時:
再帰呼び出しのアルゴリズムは「自分自身を呼び出す」わけですから、普通の上から下へ
読んでいくフローとはひと味違って、考えにくいところがあります(実は私もしばらくや
ってなかったので今回少し手こずりました)。
各行の意味を書きます。
Const nStr As String = "あいうえおかきく" '←n個の文字列
Const m As Integer = 3 '←取り出す個数
Dim n As Integer '←ご質問文のn
Dim rStr As String '←m個取り出した文字列を結合したもの
Dim mRow As Integer '←エクセル表へ書き出す際の行番号
Dim Nest As Integer '←再帰呼び出しの深さ=rStrの何文字目に取り出すのか
'-----------------------
Sub combi()
n = Len(nStr) 'nStrの文字列長をnに代入
If m > n Then Exit Sub 'nよりmが大きければ終了
rStr = String(m, " ") 'rStrにm個の空白を代入
Cells.ClearContents '書き出す表をクリア
mRow = 0 '書き出す行番号0クリア
Nest = 0 '再帰呼び出し深さ0クリア
combiPr (0) 'サブルーチン combiPr を引数0で呼び出し
End Sub
'-----------------------
Sub combiPr(n1) 'サブルーチン開始 引数はその時点での開始位置(nStrの何文字目まで処理したか)
Dim mCol As Integer '←エクセル表へ書き出す際の列番号
For nn = n1 + 1 To n - m + Nest + 1 'nnを開始位置の次の文字から始めて残りの文字数の手前までFor~Nextを繰り返す
Nest = Nest + 1 '再帰呼び出しを1カウントアップ
Mid(rStr, Nest, 1) = Mid(nStr, nn, 1) 'rStrのNest番目にnStrのnn番目を代入
If Nest = m Then 'rStrに取り出したのがm文字目なら
mRow = mRow + 1 'エクセル表の次の行へ
For mCol = 1 To m 'rStrの1文字目からm文字目まで書き出す。
Cells(mRow, mCol).Value = Mid(rStr, mCol, 1)
Next
Else 'そうでなければ、つまり現在の開始位置(=nStrの何文字目まで処理したか)がm個まで達してなければ
Call combiPr(nn) '現在の到達位置(nStrの何文字目まで処理したか)にnnをセットしてcombiPrを呼び出す(再帰呼び出し)
End If
Nest = Nest - 1'再帰呼び出しを1後退
Next
End Sub
手順は原始的なものです。
あ~く まで書かれたカードを8枚ならべて3枚抜き出すことを考えればお解りになるで
しょうか。
あ を一枚抜き出し、
い を抜き出し2枚目に置きます。
う を抜き出し、3枚目とします。←これを く まで繰り返します。
次に、い を戻して う を新たな2枚目とします。
え を抜き出し、3枚目とします。←これを く まで繰り返します。
の繰り返し・・・・
を行っているわけです。
ポイントは、1枚目を抜き出すのは か までだという点です。
き まで抜き出したら(く までしかないので)3枚目のカードがなくなります。
同様に2枚目は き までしか抜き出してはいけません。
これが「For nn = n1 + 1 To n - m + Nest + 1」の「n - m + Nest + 1」の部分の意味です。
テキストベースのみの説明なので伝えにくいのですが、不明な点があったら補足説明しますの
で、またおたずねください。
こんなにもていねいな説明にとても感謝します。
おかげでおおよその意味はつかめました。あと数回読み直し納得がいくようにいたします。
No.3
- 回答日時:
> この combiというプロシジャを起動すれば、8個から3個取り出す組み合わせが表示されるはずなんですよね。
そうです。
> しかし、何も表示されません。エラーは何もでませんが。
パラメータとか指摘する必要ありますか。
特にパラメータなど指定する必要はありません。
Excel2002/標準モジュールにて確認しましたが当方の環境では56通りの組合せが表示されます。
この回答への補足
ソフト動作をシュミレートしておおよそどのような
動きをしているのか、説明くださればありがたい。
変数の定義など
combi(0)で0を入れる意味は
No.2
- 回答日時:
再帰(的)呼び出しのアルゴリズムになると思います。
以下のソースでいかがでしょうか。
Const nStr As String = "あいうえおかきく" '←n個の文字列
Const m As Integer = 3 '←取り出す個数
Dim n As Integer
Dim rStr As String
Dim mRow As Integer
Dim Nest As Integer
'-----------------------
Sub combi()
n = Len(nStr)
If m > n Then Exit Sub
rStr = String(m, " ")
Cells.ClearContents
mRow = 0
Nest = 0
combiPr (0)
End Sub
'-----------------------
Sub combiPr(n1)
Dim mCol As Integer
For nn = n1 + 1 To n - m + Nest + 1
Nest = Nest + 1
Mid(rStr, Nest, 1) = Mid(nStr, nn, 1)
If Nest = m Then
mRow = mRow + 1
For mCol = 1 To m
Cells(mRow, mCol).Value = Mid(rStr, mCol, 1)
Next
Else
Call combiPr(nn)
End If
Nest = Nest - 1
Next
End Sub
この回答への補足
この combiというプロシジャを起動すれば、8個から3個取り出す組み合わせが表示されるはずなんですよね。
しかし、何も表示されません。エラーは何もでませんが。
パラメータとか指摘する必要ありますか。
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
このQ&Aを見た人はこんなQ&Aも見ています
関連するカテゴリからQ&Aを探す
おすすめ情報
このQ&Aを見た人がよく見るQ&A
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
タイピング
-
Word 文字が勝手に消えていく
-
筆まめ 保存が出来ません
-
WPS OFFICEでの縦書きについて
-
A4のレポート用紙1枚で2000文字...
-
パチンコ店のチラシによく使わ...
-
Notionが、テーブルビューを一...
-
Excel csvから開くと上限文字数...
-
すみません_←これってスマホか...
-
Google form グーグルフォーム...
-
「ドゥ」の簡単なローマ字入力方法
-
「一太郎2012承コンテンツ」っ...
-
ワードで住所の漢数字番地の縦...
-
ワープロソフト一太郎の「感太...
-
LINEの文字入力が少し重くなっ...
-
ワードにて スペースを全て改行...
-
入力装置に関しての質問
-
vbsでのwebフォームへの入力制限?
-
置換でピリオドを一括削除出来...
-
ヤフー知恵袋から来た連中って...
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
Notionが、テーブルビューを一...
-
Excel csvから開くと上限文字数...
-
A4のレポート用紙1枚で2000文字...
-
1MBでドレくらいの文章を書くこ...
-
フォトショップで、スキャナ取...
-
スペイン語で「i」や「o」の上...
-
イラストレーターで、文字ツー...
-
Inkscapeで文字を変形するには
-
イラストレーターで、円に沿っ...
-
ドキュワークス文書にて、フリ...
-
VB6 String型変数の文字数制限
-
10分間で1200文字打てる...
-
ペイントでのテキスト修正
-
添削文字の色の変更(一太郎)
-
イラストレイターでの文字間隔
-
パソコンソフトのシリアルナンバー
-
英文の字下げ、について
-
ラテン文字(aなどの上に点が二...
-
Lotsu Notes7 同一文章内リン...
-
作ったマクロを複数のシートで...
おすすめ情報