ホームページ  >  記事  >  バックエンド開発  >  C# の値型と参照型の詳細な紹介

C# の値型と参照型の詳細な紹介

黄舟
黄舟オリジナル
2017-10-01 07:24:471166ブラウズ

この記事では、主に C# の値型と参照型の関連情報を詳しく紹介します。興味のある方は参考にしてください。C# では、値型と参照型の 2 つの概念が非常に重要です。型を設計するときに、型インスタンスの動作を決定する必要があります。コードを記述するときに参照型と値型の違いを理解していないと、コードに不要な例外が発生します。多くの人は、これら 2 つの概念を理解していないため、プログラミング プロセスで多くの問題に遭遇します。ここで、ブロガーは値の型と参照型の理解について簡単に説明します。

まず第一に、概念的には、値型はその値を直接保存しますが、参照型はその値への参照を保存します。したがって、2 つのタイプはメモリ内の異なる場所に格納されます。

次に、メモリ空間の観点から見ると、値型はスタック上で動作するのに対し、参照型はヒープ内のストレージ ユニットを割り当てます。

スタックはコンパイル中に割り当てられるメモリ空間であり、ヒープはプログラムの実行中に動的に割り当てられるメモリ空間であり、プログラムの実行状況に応じてメモリのサイズを動的に割り当てることができます。 。したがって、値の型は常にメモリ内で事前に定義されたバイト数を占有します。参照型変数は、スタック上にメモリ空間を割り当てます。このメモリ空間には、変数の実際の値が格納されるマネージド ヒープ内のアドレスが含まれます。

つまり、バリュータイプは現金に相当し、使いたい場合は直接使用する必要がありますが、インデックスタイプは通帳に相当します。銀行で最初に入手してください。

ただし、値型はスタック上にメモリを割り当てますが、参照型はマネージド ヒープ上にメモリを割り当てます。これは単なる一般的な説明にすぎません。これについては以下で詳しく説明します。

(1) 値型のインスタンスの場合、メソッドでローカル変数として使用される場合、インスタンスはスレッド スタック上に作成され、インスタンスが型のメンバーとして使用される場合は、上位の型メンバーの一部として他の型フィールドとともにマネージド ヒープ。

すべての値型には、その型のデフォルト値を初期化する暗黙的なデフォルト コンストラクターがあります。例:

int i = new int();

は次と同等です:

Int32 i = new Int32();

は次と同等です:

int i = 0;

は以下と同等です:

Int32 i = 0;

new 演算子を使用する場合、特定の演算子のデフォルトはtype が呼び出されます。 関数を構築し、変数にデフォルト値を割り当てます。上記の例では、デフォルトのコンストラクターは値 0 を i に割り当てます。

注: C# のすべての値の型は System.ValueType から暗黙的に派生し、System.ValueType は System.Object から直接派生します。つまり、System.ValueType 自体は値型ではなくクラス型です。重要なのは、ValueType が Equals メソッドをオーバーライドし、参照アドレスではなくインスタンスの値に従って値の型が比較されることです。

(2) 参照型のインスタンスがマネージド ヒープ上に作成されます。

以下は、値型と参照型の違いを詳しく説明するコードです

​​

namespace Test 
  { 
      class Program 
      { 
        static void Main(string[] args) 
        { 
       //调用ReferenceAndValue类中的Demonstration方法 
          ReferenceAndValue.Demonstration(); 
          Console.ReadLine(); 
        } 
      } 
      public class stamp       //定义一个类 
      { 
        public string Name { get; set; }    //定义引用类型 
        public int Age { get; set; }    //定义值类型 
      } 
      public static class ReferenceAndValue   //定义一个静态类 
      { 
        public static void Demonstration()   //定义一个静态方法 
        { 
          stamp Stamp_1 = new stamp { Name = "Premiere", Age = 25 }; //实例化 
          stamp Stamp_2 = new stamp { Name = "Again", Age = 47 }; //实例化 
          int age = Stamp_1.Age;     //获取值类型Age的值 
          Stamp_1.Age = 22;     //修改值类型的值 
          stamp guru = Stamp_2;     //获取Stamp_2中的值 
          Stamp_2.Name = "Again Amend";   //修改引用的Name值 
          Console.WriteLine("Stamp_1's age:{0}", Stamp_1.Age); //显示Stamp_1中的Age值 
          Console.WriteLine("age's value:{0}", age); //显示age值 
          Console.WriteLine("Stamp_2's name:{0}", Stamp_2.Name); //显示Stamp_2中的Name值 
          Console.WriteLine("guru's name:{0}", guru.Name); //显示guru中的Name值 
        } 
    } 
  }

上記のプログラムを実行した後、Stamp_1.Age の値が変更されても、age は変更されないことがわかります。ただし、anders.Name の値を変更すると、それに応じて guru.Name も変更されます。これが値型と参照型の違いです。 age 値型変数を宣言する場合は、Stamp_1.Age の値を代入します。このとき、コンパイラはスタック上にスペースを割り当ててから、Stamp_1.Age の値を埋め込みます。両者の間には関連性はありません。これは、Stamp_1.Age の値が age にコピーされることを除いて、コンピュータ上のファイルをコピーするのと同じです。 Stamp_2 は宣言時に guru に割り当てられますが、実際には、Stamp_2 の参照も guru に割り当てられます。したがって、それらは同じブロックメモリ領域を指します。同じ領域を指しているため、誰が変更しても、クレジット カードと家族カードと同様に、家族カードでお金を引き出すと、それに関連付けられているクレジット カードのアカウントの価値もそれに応じて変わります。も変わります。

以上がC# の値型と参照型の詳細な紹介の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。