C#の不満点
個人的にC#は最高のプログラミング言語だと思っている。それでも不満点は多い。主に開発環境。
C#の不満点
- 開発環境が混沌としている(Microsoft社に振り回されて労力と時間をムダに浪費させられる)
- 開発環境
- SDK
- NuGet
- 開発環境
- 標準ライブラリが貧弱
- ロギング
- 単体テスト
- コマンド解析
- 言語仕様の後付による冗長さ
- Nullable警告
開発環境が混沌としている(Microsoft社に振り回されて労力と時間をムダに浪費させられる)
C#開発環境はこれまで大きな変化を何度もくり返してきた。その原因はMicrosoft社の経営戦略だと思っている。それに振り回されている。執筆時点の2020-11-06では、以下のように変わってきた。
- .NET Framework 〜4.0
- .NET Framework 4.5〜
- MONO
- .NET Standard
- .NET Core 〜3.x
- .NET 5.0〜
開発環境を準備するのが非常に大変である。いつもSDKの最新状況を調査し、自分のOSに適したSDKとそのインストール方法を探さねばならない。また、SDKごとに使えるパッケージのDLLが違う。ソースコードも変わる。ビルドコマンドも違う。使えるエディタも。何もかもが毎回手探りになる。開発に着手するまで大変な労力を強いられてきた。
.NET Framework
.NET Framework は Microsoft社が開発したSDKである。Windowsでしか使えない。さらにversion 4.5からはWindowsXPがサポート対象外になった。SDKなのにOSに縛られているという強い制約。そしてそのOSは有料なのにサポートが次々と打ち切られる現実。
多くの人々が強い不満と不安を抱えていたと思われる。Microsoft全盛期の時代だった。そんな独占支配された世紀末のC#開発環境に、風穴を開けたのがMONOである。
MONO
MONOは.NET FrameworkをLinuxなど他のOSでも使えるようにしたオープンソースのプロジェクトである。
まさに救世主。クロスプラットフォーム、オープンソース、自由ソフトウェア、の概念が浸透した素晴らしい時代に突入。しかし、……
再びMicrosoft社に支配される
2016年、MONOの開発元であるXamarin社はMicrosoft社に買収されてしまった。
せっかく競合していたのに、C#は再びMicrosoft社の独占市場になってしまった。CLSなので特定の言語に依存しない。それがウリだった。しかし、特定の企業に独占されてしまっている。一社の独占となると、その企業に好都合でユーザに不都合な状況が作られるのでは? これまでもそうだったように。Microsoft社に至ってはその実績が多数ある。不安で仕方ない。
たとえばGUIに関しては.NET 5.0でもWindows限定でしか対応していない。どうしても自社贔屓になっている感は否めない。Linuxなど他のOSならGtk#と連携するなどしてラッパーAPIを提供してくれたら、クロスプラットフォーム性もある素晴らしいSDKになると思うのだが……。きっとMicrosoftはそこまでやるまい。それを期待するなら、再びMicrosoft社を脅かす競合他社が現れるのを期待するしかないだろう。
一応、Eto.Forms
というサードパーティ性ライブラリはある。以前、使ったことがある。今、また当時とはSDKの状況が変わっているので、どうなっているか未確認。
.NET Core
.NET Coreは、Microsoft社が開発したオープンソースのSDK。Linuxでも使えるのが嬉しい。
CLIで開発できるようになっている。なので自動化できる。私が触ったかぎり、そのコマンド体系はわかりやすかった。
しかし、実行速度が遅すぎた。ビルドに1分くらいかかった。開発中にこの遅さは非常に辛かった。これがどうしても看過できない。結局、私はMONOを使っている。MONOなら数秒でビルドできる。雲泥の差。
かつて触ったことはあったが、今どうなっているか未確認。
- Raspbian stretch dotnet コマンドで .NET Core コンソールアプリ プロジェクトを作成&ビルドし実行できた
- Raspbian stretch dotnet コマンドで .NET Core コンソールアプリ+EFCore+SQLite3 プロジェクトを作成できた!
.NET 5.0
.NET 5.0は.NET Coreの続編。ここから名称のCore
がなくなる。
内容も大きく変わる。これまでのSDK環境を統合するらしい。買収したMONOとも統合するようなので、実行速度とクロスプラットフォーム性に期待が持てる。私は執筆時点で使ったことがない。
だが、Microsoftへの不信感は拭えない。都合の悪いことは言わず、都合のいいことしか言わないだろうから。それでも、この記事が公開される頃には素敵な開発環境になってくれていることを願う。予定では.NET 6, 7くらいまで出ているはず。
変化に対応する労力
先述のように、大きな変化を幾度もくりかえしてきた。これに対応するのが大変。
開発環境、設定、コマンド等。あらゆるものを何度も調査し構築し直すことになる。この労力と時間が非常に多い。
それに引き換え、PythonやRust言語はほぼそれだけで完結するほど完成度が高く、安定している。
標準ライブラリが貧弱
開発に最低限必要であろう以下のものさえ、第三者製ライブラリを入手せねばならない。
- ロギング
- 単体テスト
- コマンド解析
標準にもないことはないのだが、貧弱すぎて使い物にならない。
NuGet
NuGetはC#のパッケージ管理ツールである。これもSDKとは別途インストールせねばならない。インストールや使い方も要調査。
これでできるのはDLLの入手のみ。どのSDKに対するDLLを使うかの選別や、ビルドコマンドへの参照設定など、やらねばならないことがまだある。
パッケージ
開発に絶対必要なレベルのライブラリすら標準にはない。NuGetで入手せねばならない。
何をするのに、どのパッケージが必要か。それを毎回調べて、ベストプラクティスを探さねばならない。
以下は開発に必要な最低限のライブラリだと思う。それすら標準にない。
- 単体テスト
- ロギング
- コマンド引数解析
Pythonならどれも標準ライブラリにあるのに……。
さらに、実際に使ってみると使うまでのハードルもある。参照すべきDLL、using
でロードすべきDLLや名前空間、バージョンごとに異なるAPI、設定ファイルとその仕様など、多くの調査が必要。
もし公式ドキュメントがあったなら、統一的な資料でサクッと調べられただろうに……。
DLL管理が煩雑
パッケージの実体はDLLファイルである。
.NETの環境は変化する。そのSDK用にDLLファイルを作成せねばならない。NuGetで入手すればわかるが、各SDKとそのバージョンによってDLLが別ファイルになる。なので、多数のDLLの中から、どれを使うか選別せねばならない。
開発者は、そのSDK用に設定やコードを書かねばならない。利用者も自分が開発するSDKに合わせてDLLファイルを選択せねばならない。さらに、どのパッケージが、どのSDKに対応するDLLを用意してくれているかは、そのパッケージ次第である。自分の開発したいSDK用のDLLを提供してくれているとは限らない。もし提供していないなら、使えない。
つまり、SDKの変遷が激しいせいで、過去の資源であるライブラリが使えなくなるリスクを高めてしまう。これは最悪といっていい。
さらに、DLLファイル参照するためのパス管理や、それをビルドコマンドにせねばならない。統合開発環境があれば楽なのだろうが、SDKや統合開発環境も刻々と変化してしまう。よって、できるだけ全部自分で把握しておきたい。また、自動化できるようコマンドにしておきたい。なので、DLL管理が面倒になる。それは前回作った以下のコードにも現れている。
言語仕様の後付による冗長さ
C#は素晴らしい言語だが、機能を色々と後付にしているせいで冗長になってしまう部分もある。
NULL安全
たとえば、NULL安全について。NULL安全とは、NULL参照エラーを発生させない仕組みのことである。昨今ではNULLのせいで10億ドルの損失があると謳われるほど、NULLは悪しきものと認識されつつある。すでにNULL安全でない言語はレガシー言語と言われるほどだ。
C#は最初、null
を許容する言語だった。バージョン8.0にて、NULL安全機能が追加された。だが、NULL参照エラーは依然として出うる。C#は、後方互換を維持するため、null
があるとビルドエラーになるような改変をしていないためだ。結局、ビルドコマンドの引数などを渡すことで、警告を出すのがせいぜいという結果になってしまっている。
最初からNULL安全を考慮した言語設計であるRust言語などとは大違いだ。ビルドすら通らないため、これこそ真のNULL安全である。C#のそれは後付のせいで警告どまり。非常に残念。しかもnull許容する場合もありうるため、コードが複雑になってしまう。
ここだけはどうしてもC#をもちあげることができない。NULLがあったほうが簡略化できる場合もあるため、一概に悪いとも言えないと思うが。後付のせいで中途半端かつ冗長になってしまった感は否めない。
型安全
もっとも、NULL安全どころか、型安全ですらないPythonは論外である。Pythonは型安全でないせいで実行時エラーが頻出しうる。
型に関してC#は素晴らしい。ジェネリクスもあるし、タプルも実装してくれた。拡張メソッドもある。dynamic
型まである。ただ、優れた糖衣構文がもっと欲しいなどの要求はある。きっと徐々に追加されていくだろう。今後に期待。
所感
実際に触ってみてよくわかった。環境構築を手順やコードに落とし込むことが、どれだけ大変か。前回、それをやったのだが、きっとすぐに使えなくなるのだろう。やるせない思いになる。せっかくC#自体はすばらしい言語なのに……。
ふつうは統合開発環境を使えば簡単にできるという認識なのだろう。だが、それも信用できない。VisualStudio2008がWindowsでしか使えなかったように。MonoDevelopが開発終了してしまったように。Xamarinが買収されてMONOが.NET 5.0に統合されてしまうように。過去の事実が「きっと今回も統合開発環境やSDKを奪われ壊される」と囁く。
だからこそ、とにかく低レイヤを自分で制御できる状態でありたい。統合開発環境でF5
キーを押下するという方法でしかビルドする術を知らないと、ビルドすらできないハメになってしまうから。
自前でSDKを用意し、ビルドコマンドを叩く。すると、以下のようなコードを書くハメになる。大変すぎる……。もっと楽に開発したかった。
きっと.NET 5.0以降では改善しているに違いない。そう信じよう。
対象環境
- Raspbierry pi 4 Model B
- Raspberry Pi OS buster 10.0 2020-08-20 ※
- bash 5.0.3(1)-release
$ uname -a Linux raspberrypi 5.4.72-v7l+ #1356 SMP Thu Oct 22 13:57:51 BST 2020 armv7l GNU/Linux