COBOLを学ぶ皆さん、こんにちは!ベテランCOBOLエンジニアの〇〇です。
今回は、データ定義をスマートにする便利な機能「RENAMES (66レベル項目)」について、特に初心者が陥りやすい「制限事項」に焦点を当てて解説していきます。この知識は、コンパイルエラーを未然に防ぎ、より堅牢なプログラムを書くために非常に重要ですよ!
1. 導入:なぜRENAMESの制限を知る必要があるのか?
COBOLのRENAMES文(66レベル項目)は、既存のデータ項目の一部、または複数の連続するデータ項目に「別の名前」を付けることができる便利な機能です。これを使うことで、プログラムの可読性を高めたり、特定のデータ範囲をまとめて扱ったりすることができます。
しかし、どんな便利な機能にも「正しい使い方」と「使ってはいけない場面」があります。RENAMESの場合、特に「OCCURS句(配列項目)」と組み合わせようとすると、コンパイルエラーになってしまいます。なぜそうなるのか、その理由と対処法を知っておくことで、無駄な試行錯誤を減らし、スムーズに開発を進めることができるようになります。
2. 基礎知識:RENAMESとOCCURS句とは?
まずは、今回登場する主要な二つの機能についておさらいしましょう。
- RENAMES (66レベル項目)
RENAMESは、データ項目に別名(エイリアス)を付ける機能です。主に、データ構造の一部に意味のある名前を与えたり、連続する複数の項目を一つの名前で扱いたい場合に利用します。
例えば、「姓」と「名」という項目があるときに、その二つを合わせた範囲に「氏名」という別名を付ける、といった使い方ができます。レベル番号「66」を使って定義するのが特徴です。 - OCCURS句
OCCURS句は、同じ形式のデータが繰り返し出現する場合に、それを「配列」や「テーブル」として定義するための機能です。例えば、月ごとの売上データを12ヶ月分持つ場合などに使います。
OCCURS句で定義された項目は、添字(インデックス)を使って「何番目のデータ」かを指定してアクセスします。
RENAMESはデータ定義を柔軟にする一方で、OCCURS句はデータの繰り返し構造を定義します。この二つがどのように関係し、なぜ衝突するのかを見ていきましょう。
3. 実装/解決策:RENAMESとOCCURS句の制限
結論から言うと、RENAMES (66レベル項目) は、OCCURS句を含む項目、またはOCCURS句の配下にある項目を再命名することはできません。
なぜこの制限があるのでしょうか?
RENAMESは、データ部の物理的なメモリ上の固定された範囲に名前を付けます。しかし、OCCURS句を持つ項目は、添字(例:ITEM-ENTRY(1) や ITEM-ENTRY(2))によって参照する位置が動的に変わります。
もしOCCURS句を含む項目にRENAMESを許可してしまうと、RENAMESされた名前が「どの添字のデータ」を指すのかが不明確になってしまいます。コンパイラは、添字による計算(アドレス解決)ができないRENAMES項目に対して、どのデータを参照すれば良いのか判断できないため、コンパイルエラーとするのです。
RENAMESは「固定されたデータ範囲の別名」、OCCURS句は「繰り返される動的なデータ要素」と考えると、この制限の理由が理解しやすいでしょう。
4. サンプルプログラム
以下のサンプルコードを見てください。RENAMESの正しい使い方と、OCCURS句との組み合わせでエラーになる例を示します。エラーになる箇所はコメントアウトしてありますので、実際に試す際はコメントを外してコンパイルしてみてください。
IDENTIFICATION DIVISION.
PROGRAM-ID. RENAMES-OCCURS-SAMPLE.
DATA DIVISION.
WORKING-STORAGE SECTION.
— RENAMESの正しい使い方の例 (OCCURS句なし) —
01 CUSTOMER-RECORD.
05 CUSTOMER-ID PIC X(5).
05 CUSTOMER-NAME-AREA.
10 LAST-NAME PIC N(10). > 姓 (全角10文字)
10 FIRST-NAME PIC N(10). > 名 (全角10文字)
05 CUSTOMER-ADDRESS PIC N(30). > 住所 (全角30文字)
05 CUSTOMER-PHONE PIC X(12). > 電話番号
- CUSTOMER-NAME-AREA全体に”FULL-NAME”という別名を付ける
66 FULL-NAME RENAMES CUSTOMER-NAME-AREA.
- CUSTOMER-NAME-AREAからCUSTOMER-ADDRESSまでの範囲に”NAME-AND-ADDRESS”という別名を付ける
66 NAME-AND-ADDRESS RENAMES CUSTOMER-NAME-AREA THRU CUSTOMER-ADDRESS.
— OCCURS句を含む項目 —
01 SALES-DATA.
05 MONTHLY-SALES OCCURS 3 TIMES. > 月別売上データ (3ヶ月分)
10 MONTH-NO PIC 99. > 月番号
10 SALES-AMOUNT PIC 9(7). > 売上金額
— 不正なRENAMESの例 (コンパイルエラーになるケース) —
- 下記は全てコンパイルエラーになります。
- OCCURS句を含む項目 “MONTHLY-SALES” をRENAMESしようとするのはNG
- 66 FIRST-MONTH-DATA RENAMES MONTHLY-SALES.
- OCCURS句の配下にある項目 “MONTH-NO” をRENAMESしようとするのはNG
- (たとえ添字を付けなくても、元の定義がOCCURS句の配下であるため)
- 66 FIRST-MONTH-NUMBER RENAMES MONTH-NO.
- OCCURS句の配下にある項目を範囲指定でRENAMESしようとするのもNG
- 66 MONTH-DETAILS RENAMES MONTH-NO THRU SALES-AMOUNT.
PROCEDURE DIVISION.
MAIN-LOGIC.
DISPLAY “— RENAMESの正しい使い方の例 —“.
MOVE “00123” TO CUSTOMER-ID.
MOVE “山田” TO LAST-NAME.
MOVE “太郎” TO FIRST-NAME.
MOVE “東京都新宿区西新宿1-1-1” TO CUSTOMER-ADDRESS.
MOVE “090-1234-5678” TO CUSTOMER-PHONE.
DISPLAY “顧客ID: ” CUSTOMER-ID.
DISPLAY “元データ(CUSTOMER-NAME-AREA): ” CUSTOMER-NAME-AREA.
DISPLAY “RENAMES項目(FULL-NAME): ” FULL-NAME. > RENAMESで定義した別名
DISPLAY “RENAMES項目(NAME-AND-ADDRESS): ” NAME-AND-ADDRESS. > RENAMESで定義した範囲項目
DISPLAY ” “.
DISPLAY “— OCCURS句を含む項目へのRENAMESはコンパイルエラーとなります —“.
DISPLAY “上記のコメントアウトされたRENAMES文を有効にするとエラーが発生します。”.
DISPLAY “コンパイラは「OCCURS句を含む項目はRENAMESできない」といったメッセージを出力するでしょう。”.
STOP RUN.
5. 応用・注意点:現場で役立つ補足情報
- エラーメッセージの例:
コンパイラによってメッセージは異なりますが、例えば「RENAMES SUBJECT CANNOT CONTAIN AN OCCURS CLAUSE」や「RENAMES SUBJECT IS PART OF AN OCCURS CLAUSE」といったエラーが表示されることが多いです。これらのメッセージを見たら、「あ、OCCURS句を含む項目をRENAMESしようとしているな」とピンと来てください。 - 代替手段:
もしOCCURS句の特定の要素やその範囲を「別の名前」で扱いたい場合は、RENAMESではなく、以下のような方法を検討してください。- MOVE文で作業用項目にコピーする:
必要な要素を一度、OCCURS句を持たない作業用項目にMOVEし、その作業用項目を処理します。
例:01 WS-SINGLE-MONTH-SALES. 05 WS-MONTH-NO PIC 99. 05 WS-SALES-AMOUNT PIC 9(7).
MOVE MONTHLY-SALES(1) TO WS-SINGLE-MONTH-SALES. - 参照変更 (Reference Modification) を使う:
データ項目の一部を、開始位置と長さを指定して直接参照する方法です。これはRENAMESとは異なり、動的な参照が可能です。
例:DISPLAY MONTHLY-SALES(1)(1:2)(1番目の月の月番号を表示)
- MOVE文で作業用項目にコピーする:
- データ構造の設計:
RENAMESを使いたいのにOCCURS句が邪魔になる場合は、そもそもデータ構造の見直しが必要かもしれません。本当にそのデータがOCCURS句であるべきか、またはRENAMESを使わずに処理できる代替手段はないか、設計段階で考慮することが大切です。
RENAMESは非常に便利な機能ですが、その制限を理解し、適切に使いこなすことがベテランへの第一歩です。特にOCCURS句との組み合わせには注意して、効率的でエラーの少ないCOBOLプログラムを目指しましょう!

コメント