これはなんなのでしょうか?


goro  2005-11-07 09:34:07  No: 18487

お世話になります。

(基本的なことでしたら申し訳ありません)
Windows.pas を眺めてたら、以下の記述がありました。

>type
>  PLDTEntry = ^TLDTEntry;
>  _LDT_ENTRY = record
>    LimitLow: Word;
>    BaseLow: Word;
>    case Integer of
>      0: (
>        BaseMid: Byte;
>        Flags1: Byte;
>        Flags2: Byte;
>        BaseHi: Byte);
>      1: (
>        Flags: Longint);
>  end;

typeの定義全体の意味はいいのですが、
>    case Integer of
>      0: (
>        BaseMid: Byte;
>        Flags1: Byte;
>        Flags2: Byte;
>        BaseHi: Byte);
>      1: (
>        Flags: Longint);
この部分(case Integer of ...)は、どのような動きというか、
なんなのでしょうか?
(実装部でのcase文なら分かるのですが・・・)


union  2005-11-07 10:09:27  No: 18488

ヘルプでrecord型について参照してみてください。
レコードの可変部分というところに説明があります。
Cで言うところの共用体に相当します。
Cのソースのunionをpascalで書くとこうなります


さどやま  URL  2005-11-08 06:38:41  No: 18489

私もこれの理解には長い間苦しみました。

> レコードの可変部分というところに説明があります
  Delphi7 では、ヘルプの「目次」で
  Delphi言語リファレンス->データ型と変数->構造化型->レコード型 を辿ると見つかります。しかし、これを読んでも腹には落ちませんでした。
  スッキリしたのは、TRect の定義をヘルプで見たときです。

  さどやま語に翻訳すると
  BaseLow: Word;  の行までが、「不変部分」とでもいうべきもので、通常の record型と同じ理解でよい。
  case Integer of 以降が「可変部分」である。

var
  B: Byte;
  C: Word;
  LDTEntry: _LDT_ENTRY;
begin
  LDTENTRY.BaseMid := 4; 
  と記述すれば、コンパイラは case 0 の場合と判断してコンパイルする。
  LDTENTRY.Flags := $FFFFF; 
  と記述すれば、case 1 の場合とされる。

  続いて
  B := LDTENTRY.BaseMid;  // これは当然セーフ
  C := LDTENTRY.Flags;

  label1.Caption := IntToHex(C, 8);
  とすると、コンパイルはとおるが、C は Word型に切り詰められて $FFFF となる。

  _LDT_ENTRY の場合、2種類のみで使い分ければよいので、  
  _LDT_ENTRY2 = record
    LimitLow: Word;
    BaseLow: Word;
    case Boolean of    // Boolean を使用
      true: (
        BaseMid: Byte;
        Flags1: Byte;
        Flags2: Byte;
        BaseHi: Byte);
      false: (
        Flags: Longint);
  end;
  と記述しても同じことである。

  3種類以上で使い分けたい場合は、
  _LDT_ENTRY = packed record
    LimitLow: Word;
    BaseLow: Word;
    case Integer of
      0: (
        BaseMid: Byte;
        Flags1: Byte;
        Flags2: Byte;
        BaseHi: Byte);
      1: (
        Flags: Longint);
      2: (....);
      .......
      n: (.....);
  と記述すればよい。

  同様に、Case Integer of の Integer 部分は、case文で使用可能な型なら何でも使える。


※返信する前に利用規約をご確認ください。

※Google reCAPTCHA認証からCloudflare Turnstile認証へ変更しました。






  このエントリーをはてなブックマークに追加