ここではreadonlyキーワードを学びます。
readonlyキーワード
readonlyとは、read + onlyで読み取り専用を意味します。
例えばフィールドに書くことができ、そうすると読み取り専用のフィールドになります。
namespace Sample
{
public class Test
{
public readonly int MaxValue = 1000;
}
internal class Program
{
static void Main(string[] args)
{
var obj = new Test();
// 読み取り専用に代入するとビルドエラー
//obj.MaxValue = 10;
Console.WriteLine(obj.MaxValue);
}
}
}
部分的に抜き出すとここです。
public readonly int MaxValue = 1000;
正直、他にもいくつか記述可能な場所があるのですが、ほぼフィールドに記述するパターンしか使いません。
他にはreadonly structとかref readonly等があります。まぁ、興味ある人は公式を読んでください。
https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/keywords/readonly
でっ、このreadonlyですが、読み取り専用なので初期化のタイミングが制限されます。
先程のようにフィールド宣言時に同時に初期化するか、コンストラクタ内でのみ初期化が可能です。
namespace Sample
{
public class Test
{
public readonly int MaxValue;
public Test()
{
// コンストラクタ内でのみ初期化が可能
this.MaxValue = 1000;
}
}
internal class Program
{
static void Main(string[] args)
{
var obj = new Test();
// 読み取り専用に代入するとビルドエラー
//obj.MaxValue = 10;
Console.WriteLine(obj.MaxValue);
}
}
}
定数(constants)との違い
似た単語にconstがありますがconstは定数です。この定数とはコンパイル時点で確定してる必要があります。
つまり、0とか1みたいな数値、または文字列やnullしかconstを指定することはできません。
ここではC#の定数を学びましょう。定数 (constants)定数とは名前の通りで固定された値です。つまりは変数のように値を変更することができません。また、仮に定数を変更しようと試みるとビルドエラーになるので、変更するという行為自体が禁止されます。これのメリットは、コーディングのミス等で本来変えてはいけない数値を触る危険性を回避できます。また、定数は変数のように名前を与えることができるので、0や1など意味不明な数値を減らすことができます。定数を定義する方法...
対してreadonlyは初期化した値の読み取り専用を意味するため、どんな値でもreadonly化できます。
例えばクラス型にreadonlyを付けると、インスタンス生成後に書き換えできないインスタンスを作れます。
namespace Sample
{
public class Test
{
public readonly Position Pos;
public Test()
{
this.Pos = new Position()
{
X = 32,
Y = 64,
};
}
}
public class Position
{
public int X { get; set; }
public int Y { get; set; }
}
internal class Program
{
static void Main(string[] args)
{
var obj = new Test();
// 読み取り専用なのでビルドエラー
//obj.Pos = new Position();
Console.WriteLine($"X={obj.Pos.X}, Y={obj.Pos.Y}");
}
}
}
注意というか、C#では常識の話ですが、これはクラスのインスタンスがreadonlyなので、読み取り専用なのは参照値です。
つまり、参照値が示す先のクラスが所有するオブジェクトは書き換えが可能です。ここに疑問を感じる人は以下を読んでください。
関数(※1)を学んだことで、ついに値型と参照型の違いを知ることができます。ここではC#で最重要とも言える値型と参照型の違いを理解しましょう。※1現在の知識を踏まえて、ここではメソッドではなく関数と呼びます。値型と参照型の復習まずは値型と参照型について復習しましょう。この2つは値を保存する場所が大きなポイントになります。値型値型とは用意した領域に直接的に値を保存します。参照型参照型は値を別の領域に格納し、それを...
staticと併用する方法
const化できないフィールドをconstのように利用したい場合はstaticを併用します。
と言うのも、constはクラスに所属するため扱い的にはstaticの上位板です。
ここではC#のstaticについて学びます。staticstaticは静的クラスや静的メンバを作成する時に利用します。実はサンプルで既に利用していて、Main関数がstatic宣言されてます。static void Main(string[] args)では、このstaticは何を意味するのでしょうか? 静的とは「動かない」とか「一定」と言う意味らしいです。より簡単に言うと、staticを付けたクラスやメソッドはアプリケーションで1つだ...
なので、readonlyのみではインスタンスに所属する読み取り専用のフィールドにしかなりません。
その値がインスタンスごとに異なる必要がないなら、staticを付けてクラスに所属させた方が良いです。
namespace Sample
{
public class Test
{
public static readonly Position Pos = new Position()
{
X = 32,
Y = 64,
};
}
public class Position
{
public int X { get; set; }
public int Y { get; set; }
}
internal class Program
{
static void Main(string[] args)
{
// クラスに属するので、アクセスはこうなる。
Console.WriteLine($"X={Test.Pos.X}, Y={Test.Pos.Y}");
}
}
}
定数っぽく使いたいけどconstが無理ってパターンは凄く多い。そんな時にreadonlyを使おう。
あとがき
readonlyなんて、このパターンだけ覚えておけば十分。
◆ C#に関する学習コンテンツ
この記事は参考になりましたか?
コメント