「大人の教養・知識・気付き」を伸ばすブログ

一流の大人(ビジネスマン、政治家、リーダー…)として知っておきたい、教養・社会動向を意外なところから取り上げ学ぶことで“気付く力”を伸ばすブログです。

MENU

【プログラム】1週間でC#の基礎が学べる本(4/6)

 C#を使うようにはなったものの、具体的な機能については未習熟なので(というかまだ使うべき状況が出てきていないので)

を読んで、まずは最低ラインを学んでいく。

7. オブジェクト指向

7.1 クラスとオブジェクト

 オブジェクト指向は「あらゆるものをすべて『モノ』として表現するという考え方」を指す。オブジェクトには、操作に当たる「メソッド」とデータに当たる「フィールド」から構成される。更にそれらを定義づけるクラスという概念も存在する。実際にはその定義されたクラスをインスタンスとして生成する。

 クラスは以下で宣言する:

class クラス名
{
   フィールド/メソッドの定義
}

メソッドを定義するとき、戻り値を不要とする場合は型指定をvoidとする。慣習としてC#ではクラス名とファイル名を一致させる

 インスタンスのフィールドおよびメソッドは以下で代入・呼び出す:

(インスタンス名).(フィールド)
(インスタンス名).(メソッド名)(引数1, 引数2, \cdots)

なお自分自身をインスタンスとして指定する場合はフィールドと引数を明確に区別すべくthisとする。
 メソッド・フィールドを命名する際は、慣習として、

  • フィールド:小文字の英単語および単独の個文字のアルファベットを利用する。
  • メソッド:最初の一文字目は大文字とした英単語。複数の単語の組み合わせとして命名する場合は各単語の先頭も大文字とする。

例:
 GetData

7.2 オブジェクトの定義例

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ExampleProblem401
{
    // クラスの定義
    class Person
    {
        // 名前(フィールド)
        public string name = "";

        // 年齢(フィールド)
        public int age = 0;

        // 情報の表示(メソッド)
        public void ShowAgeAndName()
        {
            Console.WriteLine("名前:{0} 年齢:{1}", name, age);
        }

        // 情報の設定
        public void SetAgeAndName(string name, int age)
        {
            this.name = name;
            this.age = age;
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            Person P1, P2;

            P1 = new Person();  // インスタンスの生成
            P2 = new Person();  // インスタンスの生成

            P1.name = "山田太郎";
            P1.age = 19;

            P2.SetAgeAndName("佐藤花子",23);

            P1.ShowAgeAndName();
            P2.ShowAgeAndName();
        }
    }
}

7.3 オーバーロード

 同一のクラスにおいて同名のメソッドを複数定義することをオーバーロードという。オーバーロードする場合、それぞれ引数及び戻り値の型、数が異なっている必要がある。

8. カプセル化

 クラスの複雑な仕組みは可能な限り隠蔽し必余殃最低限の操作で外部から操作できるようにすることをカプセル化という。
 すべてのフィールドで外部からの操作を禁止するのは非現実的であるため、フィールドにアクセスするための専用メソッドを追加して対応する:

  • セッター(setter):フィールドの値を変更するメソッド
  • ゲッター(getter):フィールドの値を取得するメソッド

8.1 アクセス修飾子

 フィールドおよびメソッドへのアクセス制限を指定するために用いるのがアクセス修飾子である。

名前
意味
public どこからでもアクセスできる。
protected 同一クラスかサブクラスからしかアクセスできない。
internal 同一のアセンブリでのみアクセスできる。
protected internal protectedかつinternal
private 同じクラス内からアクセスできない。

8.2 プロパティ

 C#カプセル化をするためにsetterおよびgetterを記述するための仕組みをプロパティという。

アクセス修飾子 型名 プロパティ名
{
  set
  {
    // setter
    // ここに値変更時の処理を書く。
    // valueという名前の変数に代入された値が格納される。
  }
  get
  {
    // getter
    // ここに値の取得時の処理を書く。
    // メソッドの場合と同様に値はreturnで返す。
  }
}

public string Name
{
  set { name = Value; }
  get { return name; }
}

9. インスタンスの生成と消去

9.1 コンストラク

 インスタンス生成時に一度だけ呼び出される特殊なメソッドとしてコンストラクがある。主にクラスの初期化に利用される。クラス名と同名を持たせる。

class Square2
{
  public float width;
  public float height;

  public Square2(float width, float height)
  {
    this.width = width;
    this.height = height;
  }
}

9.2 ガーベージコレクションとメモリ管理

 C#にはメモリを使い切らないように不要なインスタンスを整理するガーベージコレクションが用意されている。
 どのタイミングでガーベージコレクションが動作するかはユーザーには分からないものの、

GC.Collect();

で意図的に起動することが出来る。削除対象の判別はその変数・インスタンスがnullであること(メモリ内に存在するものの使用されていない)で行う。

9.3 デストラク

 インスタンスを破棄するときに呼び出す特殊なメソッドにデストラクがある*2

~(クラス名)()

で宣言する。引数は不要で、アクセス修飾子は付けない。

9.4 値型と参照型

 C#における変数の型は2つに大別できる:

  • 値型:データそのものを格納する。
  • 参照型:別の場所に確保されているデータへの参照先情報のみを格納する。

参照型を扱う場合、ガーベージコレクションが発動するためにはインスタンスが参照を完全に失う必要がある

9.4.1 スタックとヒープ

 C#において、値が多変数が保存される変数の領域をスタックという。その変数を定義している処理のスコープを抜けると、スタック領域の変数は自動的にメモリから消去される。これに対し、new演算子を用いて生成するデータが存在するメモリ領域をヒープという。ヒープはガーベージコレクションで消去される。

9.4.2 例題
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ExampleProblem407
{
    class Student
    {
        private string name;
        private int grade;
        private int age;
        public Student(string name, int grade, int age)
        {
            SetInformation(name, grade, age);
        }
        public void SetInformation(string name, int grade, int age)
        {
            this.name = name; this.grade = grade;
            this.age = age;
        }

        public void ShowInformation()
        {
            Console.WriteLine("名前:{0} 学年:{1} 年齢:{2}", name, grade, age);
        }
    }
}


using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ExampleProblem407
{
    class Program
    {
        static void Main(string[] args)
        {
            Student[] students = new Student[3];

            students[0] = new Student("高貴", 3, 18);
            students[1] = new Student("勇一", 2, 17);
            students[2] = new Student("花子", 1, 16);

            foreach(Student s in students)
            {
                s.ShowInformation();
            }
        }
    }
}

*1:「WINGSプロジェクト 土井毅,髙江賢,飯島聡(2012)[改訂新版]C#ポケットリファレンス」(技術評論社)P.77参照。

*2:何のためにこれが必要なのか。ものの本(Ian Griffiths 著、木下 哲也訳(2021)「プログラミングC# 第8版」)によれば、「主にデストラクタはCLRの管理外で生存するもののハンドラを扱うためだけに役立」つ(同P.327)としている。残念ながらあまりよく分からない…。

プライバシーポリシー お問い合わせ