c#のメモリ割り当てを可視化するツール

SharpLabツールでは、ILに変換した時の状態や、メモリの内部割り当ての状態をビジュアルに確認できる機能があります

メモリ割り当て状態の確認

ヒープ上の確認

Inspect.Heap()メソッド

スタック上の確認

Inspect.Stack()メソッド

スタック領域のサイズは、規定では1MBです

変数の状態の確認

Inspect.MemoryGraph()メソッド

値型と参照型

int型は、値型です。値型はスタック領域に保存されます
string型は、参照型です。参照型はヒープ領域に保存されます

値が入っている場合

int number = 3;

Inspect.MemoryGraph(number);

string name = "太郎";

Inspect.MemoryGraph(name);

値が入っている場所が指されていない場合

int? number = null;

Inspect.MemoryGraph(number);

string name = null;

Inspect.MemoryGraph(name);

構造体

Vec a = new Vec();
Vec b = new Vec();

a.x = 3;
b.x = 4;

Vec[] c = new Vec[2] { a, b };

Inspect.Stack(a);
Inspect.MemoryGraph(a);

Inspect.Stack(b);
Inspect.MemoryGraph(b);

Inspect.Heap(c);

Inspect.MemoryGraph(c);

struct Vec
{
    public int x;
    public int y;
}

クラス(Player)

var playerA = new Player();
var playerB = new Player();

playerA.name = "太郎";
playerA.score = 3;

playerB.name = "二郎";
playerB.score = 4;

var Players = new Player[2]{playerA,playerB};

Inspect.Heap(playerA);
Inspect.Heap(playerB);
Inspect.Heap(Players);

Inspect.MemoryGraph(Players);

class Player
{
    public string name;
    public int score;
}

クラス(Car)

using System;

class Engine
{
    private int _power;
    public int Power
    {
        get { return _power; }
        set { _power = value; }
    }

    public void Start()
    {
        Console.WriteLine("Engine started.");
    }

    public void Stop()
    {
        Console.WriteLine("Engine stopped.");
    }
}

class Car
{
    private Engine _engine;
    public Engine Engine
    {
        get { return _engine; }
        set { _engine = value; }
    }

    private string _name;
    public string Name
    {
        get { return _name; }
        set { _name = value; }
    }

    public void Start()
    {
        Console.WriteLine(Name + " started.");
        _engine.Start();
    }

    public void Stop()
    {
        Console.WriteLine(Name + " stopped.");
        _engine.Stop();
    }
}

class Program
{
    static void Main()
    {
        Car car = new Car();
        car.Name = "My car";
        car.Engine = new Engine();
        car.Engine.Power = 100;
        car.Start();
        car.Stop();
        
        Inspect.Heap(car);
        Inspect.Heap(car.Engine);
        
        Inspect.MemoryGraph(car);

    }
}

クラス(Car、エンジンが2つ)

using System;
using System.Collections.Generic;

class Engine
{
    private int _power;
    public int Power
    {
        get { return _power; }
        set { _power = value; }
    }

    public Engine(int power)
    {
        this.Power = power;
    }

    public void Start()
    {
        Console.WriteLine("Engine started.");
    }

    public void Stop()
    {
        Console.WriteLine("Engine stopped.");
    }
}

class Car
{
    private List<Engine> _engine;
    public List<Engine> Engine
    {
        get { return _engine; }
        set { _engine = value; }
    }

    private string _name;
    public string Name
    {
        get { return _name; }
        set { _name = value; }
    }

    public void Start()
    {
        Console.WriteLine(Name + " started.");
        _engine[0].Start();
    }

    public void Stop()
    {
        Console.WriteLine(Name + " stopped.");
        _engine[0].Stop();
    }
}

class Program
{
    static void Main()
    {
        Car car = new Car();
        car.Name = "My car";
        car.Engine = new List<Engine>();
        car.Engine.Add(new Engine(100));
        car.Engine.Add(new Engine(200));

        //car.Engine.Power = 100;
        car.Start();
        car.Stop();

        Inspect.Heap(car);
        Inspect.Heap(car.Engine);

        Inspect.MemoryGraph(car);

    }
}

クラス(動物、継承、インターフェース)

using System;
using System.Collections.Generic;

interface IBehavior
{
    void Fly();
}

abstract class Animal
{
    public string name;
    public int age;

    protected Animal(string name, int age)
    {
        this.name = name;
        this.age = age;
    }

    public abstract void Meow();

}

class Cat : Animal
{
    public Cat(string name, int age) : base(name, age)
    {
    }

    public override void Meow()
    {
        Console.WriteLine("にゃー");
    }
}

class Crow : Animal, IBehavior
{
    public Crow(string name, int age) : base(name, age)
    {
    }

    public void Fly()
    {
        Console.WriteLine("優雅に飛べる");
    }

    public override void Meow()
    {
        Console.WriteLine("カー");
    }
}


class Program
{
    static void Main()
    {
        Animal cat = new Cat("たま", 3);
        Animal crow = new Crow("かんた", 2);

        Animal[] animals = new Animal[] { cat, crow };

        foreach (var animal in animals)
        {
            animal.Meow();
        }

        Inspect.Heap(cat);
        Inspect.Heap(crow);

        Inspect.MemoryGraph(animals);
    }
}

参考

C#,学習,設計

Posted by hidepon