Macで簡単なC#ファイルのコンパイルと実行をVSCode上で自動化する方法

# 背景
**C#** は通常Visual Studio（Windowsの場合）やVisual Studio for Mac（Macなどの場合）上で開発・実行されますが，サンプルコードを動かしてみたり，競技プログラミングでテストをしてみたりするときなど，簡単なソースコードをすぐに実行したいことがあります．実はC#は先述したような統合開発環境（IDE）を使用しないでも，ターミナルからコマンドでコンパイルし，実行することが可能です．私の大好きな後輩が競技プログラミングを始めるに際してC#の実行方法について悩んでいたので，ここではVSCodeの拡張機能であるCode Runnerを使用して，コマンドひとつでC#のコンパイルおよび実行を行えるようにする手順を紹介したいと思います．

# C#のコンパイルと実行の方法
Windowsの場合，`.NET Framework`と呼ばれるフレームワークの中に，C#のコンパイラである`csc.exe`が標準装備されています．しかし，この`.NET Framework`はMicrosoft社がWindows上でのみ利用することを想定して開発したものであるため，Windows以外のOSでは使えません．そこで，ここではクロスプラットフォームの.NET実行環境である`Mono`を使用します．MonoはMacやLinux系OSで使うことができます．

### 公式サイト
https://www.mono-project.com/

### Monoについて
> *Sponsored by Microsoft, Mono is an open source implementation of Microsoft's .NET Framework as part of the .NET Foundation and based on the ECMA standards for C# and the Common Language Runtime. A growing family of solutions and an active and enthusiastic contributing community is helping position Mono to become the leading choice for development of cross platform applications.*
(https://www.mono-project.com/より)

# Monoをインストールする
Homebrewからインストールするのが良いでしょう．ターミナルで以下を実行します．
```console:terminal
brew install mono
```

# C#を実行してみる
### サンプルコード
以下は`Hello　World!`を出力するサンプルプログラムです．
```csharp:hello.cs
using System;

public class HelloWorld {
    static public void Main() {
        Console.WriteLine("Hello World!");
    }
}
```

試しに，上記プログラムをコンパイルして，実行してみましょう．先ほど説明したように`.NET Framework`では`csc`コマンドを用いることができますが，`Mono`では代わりに**mcs(Mono C# Compiler)** コマンドを使います．以下をコンパイルしたいファイルのあるディレクトリの上で叩いてみましょう．
```console:terminal
mcs hello.cs
```
エラーを吐かず，`hello.exe`というファイルが生成されていれば，成功でしょう．

次に実行です．実行には**mono** コマンドを使います．以下をターミナルで叩いてください．
```console:terminal
mono hello.exe
```
結果は以下のようになります．
```console:terminal
Hello World!
```
無事実行できたでしょうか．以上がコンパイルから実行までの流れになります．まとめると，
1. `csc`コマンドでコンパイルする．
2. `mono`コマンドで実行する．

という流れです．

# VSCodeで自動化する
コンパイルと実行の流れはそこそこ長いコマンドを叩かなければならないため，少々面倒です．VSCodeでは **Code Runner** というコマンドをショートカットひとつで打ち込んでくれる拡張機能が存在します．これを使いましょう．

### VSCodeのインストール
VSCodeをインストールしていない方は，以下よりインストールしてください．

https://code.visualstudio.com/download

### Code Runnerのインストール
VSCodeの拡張機能をタブ（下記画像部分）を開いて，`"Code Runner"`と検索し，インストールしてください．
![スクリーンショット 2023-10-13 0.20.30.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3457534/353486ee-a19b-24ad-ef03-11102d5c30c3.jpeg)

ついでにここで，C#の拡張機能をインストールしても良いでしょう．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3457534/5e295478-182a-bd0a-5c5b-bd3cb1ca4a05.png)

### コマンドをカスタマイズ
Code Runnerは`command` + `control` + `N`のショートカットで，ターミナルにコードのプログラミング言語に応じたコンパイル＆実行のコマンドを打ち込んでくれます．打ち込んでくれるコードは，`defaultSettings.json`内で定義されています．
```json:defaultSettings.json
"code-runner.executorMap": {
	"javascript": "node",
	"java": "cd $dir && javac $fileName && java $fileNameWithoutExt",
	"c": "cd $dir && gcc $fileName -o $fileNameWithoutExt && $dir$fileNameWithoutExt",
	"zig": "zig run",
	"cpp": "cd $dir && g++ $fileName -o $fileNameWithoutExt && $dir$fileNameWithoutExt",
	"objective-c": "cd $dir && gcc -framework Cocoa $fileName -o $fileNameWithoutExt && $dir$fileNameWithoutExt",
	"php": "php",
	"python": "python -u",
	"perl": "perl",
	"perl6": "perl6",
	"ruby": "ruby",
	"go": "go run",
	"lua": "lua",
	"groovy": "groovy",
	"powershell": "powershell -ExecutionPolicy ByPass -File",
	"bat": "cmd /c",
	"shellscript": "bash",
	"fsharp": "fsi",
	"csharp": "scriptcs",
	"vbscript": "cscript //Nologo",
	"typescript": "ts-node",
	"coffeescript": "coffee",
	"scala": "scala",
	"swift": "swift",
	"julia": "julia",
	"crystal": "crystal",
	"ocaml": "ocaml",
	"r": "Rscript",
	"applescript": "osascript",
	"clojure": "lein exec",
	"haxe": "haxe --cwd $dirWithoutTrailingSlash --run $fileNameWithoutExt",
	"rust": "cd $dir && rustc $fileName && $dir$fileNameWithoutExt",
	"racket": "racket",
	"scheme": "csi -script",
	"ahk": "autohotkey",
	"autoit": "autoit3",
	"dart": "dart",
	"pascal": "cd $dir && fpc $fileName && $dir$fileNameWithoutExt",
	"d": "cd $dir && dmd $fileName && $dir$fileNameWithoutExt",
	"haskell": "runghc",
	"nim": "nim compile --verbosity:0 --hints:off --run",
	"lisp": "sbcl --script",
	"kit": "kitc --run",
	"v": "v run",
	"sass": "sass --style expanded",
	"scss": "scss --style expanded",
	"less": "cd $dir && lessc $fileName $fileNameWithoutExt.css",
	"FortranFreeForm": "cd $dir && gfortran $fileName -o $fileNameWithoutExt && $dir$fileNameWithoutExt",
	"fortran-modern": "cd $dir && gfortran $fileName -o $fileNameWithoutExt && $dir$fileNameWithoutExt",
	"fortran_fixed-form": "cd $dir && gfortran $fileName -o $fileNameWithoutExt && $dir$fileNameWithoutExt",
	"fortran": "cd $dir && gfortran $fileName -o $fileNameWithoutExt && $dir$fileNameWithoutExt",
	"sml": "cd $dir && sml $fileName",
	"mojo": "mojo run"
}
```
このファイルでは，プログラミング言語の種類と，ショートカットキーを押したときにターミナルに打ち込まれるコマンドの対応関係を示しています．C#の部分を見てみると，`"csharp": "scriptcs",`となっており，これはmonoによるコンパイル＆実行コマンドと一致していません．ですので，User SettingsのJSONにmonoのコマンドを打ち込むような設定を上書きしてしまいましょう．`setting.json`は，`command` + `shift` + `p`でコマンドパレットを開き，画像のように，
```text
Open User Settings
```
と打ち込んで開くことができます．

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3457534/0adf14da-0e03-a374-4cfb-eae0ff85edb9.png)

開くことができたら以下を追記してください.記述する場所はどこでもいいです．

```json::settings.json
"code-runner.executorMap": {
  "csharp": "mcs $fileName && mono $fileNameWithoutExt.exe ",
}
```
:::note warn
前後のオブジェクトとの間にカンマを忘れずに！
:::

### ショートカットでコンパイル＆実行してみる
いよいよショートカットによるコンパイル＆実行です．`hello.cs`に戻って，`command` + `control` + `N`を押下してください．うまくいけば，以下のように実行されるでしょう．
```console:terminal
% mcs hello.cs && mono hello.exe
Hello World!
```
ここまでできたら完了です．

# まとめ
以上の手順により，VSCode上でC#プログラムのショートカットによる自動コンパイル＆実行ができるようになりました．これで僕の後輩もより一層C#の勉強に精を出してくれることでしょう．今度お礼でもしてください．

# 参考サイト
- [MacでC#のコードをコンパイルして実行する - Qiita](https://qiita.com/matsuda_sinsuke/items/76068f4c396887459803)
- [Code Runnerを使いこなす - Qiita](https://qiita.com/take_me/items/6a1d2d417889837219d1)