C#er、Delphiを学ぶ②（どうやってDelphiを学ぶか？）

# C#er、Delphiを学ぶ
ある程度C#を知っている人がどうやってDelphi学んだか、過程を共有できたらうれしいなぁーと。方法論や戦略がごちゃまぜですが悪しからず。間違ってたら、コメントくださいm(__)m

# 文法の比較サイト
「Delphiのこの文法、C#でいう何？」って時に見れるサイトがあると嬉しいんだが、日本語のサイトがなかなか見つからん。↓のサイトはなんだかんだで重宝してる。もっといいサイトはあるはず。~~というか何で見つかんねぇんだ。~~

- [Delphi and C# Cross Reference Guide](https://m.prestwood.com/ASPSuite/KB/CrossRef.asp?LangID=2&ToLangID=6&View=All)
- [An (incomplete) comparison of Delphi and C# features](https://web.archive.org/web/20200410122840/http://www.gekko-software.nl/DotNet/Art01.htm)

# 拡張子について
まず、Delphiの拡張子はC#でいうなに？ってのが分からんかったので、↓にまとめた。

|Delphi  |C#  |備考 |
|---|---|---|
|.pas  |.cs  |ソースコードを記述する |
|.dfm   |.designers.cs  |VCL等のGUIの定義を記述する |
|.dpr  |.csproj & Program.cs  |EXE等のエントリーポイントにあたる |
|.dproj   |.csproj  |プロジェクトファイル |
|.groupproj   |.sln  |複数のプロジェクトを管理するファイル |

## 参考
- [今更聞けない Delphi のコト (拡張子編)](https://ht-deko.com/tech025.html)
- [RAD Studio によって生成されるファイルの拡張子](https://docwiki.embarcadero.com/RADStudio/Alexandria/ja/RAD_Studio_%E3%81%AB%E3%82%88%E3%81%A3%E3%81%A6%E7%94%9F%E6%88%90%E3%81%95%E3%82%8C%E3%82%8B%E3%83%95%E3%82%A1%E3%82%A4%E3%83%AB%E3%81%AE%E6%8B%A1%E5%BC%B5%E5%AD%90)
- [What is a Delphi DCU file?](https://stackoverflow.com/questions/24665856/what-is-a-delphi-dcu-file)
- [The basics of Delphi programs](http://delpysuite.sourceforge.net/program_basics.html)

# 変数やクラス名の接頭辞や接尾辞について
引数の接頭辞に「A」「F」「T」「E」つけたり、接尾辞に「U」つけたり、C#にない文化で理解できなかったのでまとめる。

|接尾辞/接頭辞  |英語 |意味　|
|---|---|---|
|A  |Argument  |引数  |
|F   |Field  |フィールド  |
|T  |Type  |型  |
|E   |Exception  |例外  |
|I   |Interface  |インターフェース  |
|U   |Unit  |ユニット  |
|L   |Local  |ローカル変数  |

## 参考
- [why certain parameters are prefixed with an a in delphi](https://stackoverflow.com/questions/8612609/why-certain-parameters-are-prefixed-with-an-a-in-delphi)
- [is there a distinct name for prefix notation used in delphi oftenl](https://stackoverflow.com/questions/6326427/is-there-a-distinct-name-for-prefix-notation-used-in-delphi-oftenly)

# C#erがビックリする文法
## {$R *.DFM} 
VCLのアプリを作ると出くわすおまじない。一見コメントのように見えるが、dfmファイルを見つけて 実行ファイルにリンクさせる命令（コンパイラ命令）のことらしい。

コンパイラ指令の使い道としてたとえば、privateな関数のテストコードを書くときにコンパイラ指令を使うんだそうな(う、嘘だろ...)。
```pascal
private
{$IfDef TEST}
public
{$EndIf}
```
- [クラスとユニット](http://ext-web.edu.sgu.ac.jp/HIKO/Delphi01/chap11/pb1106.html)
- [Delphiコンパイラ指令一覧](https://ohmix.net/memo/deldir/)
- [How can I test private methods with DUnit?](https://stackoverflow.com/questions/422379/how-can-i-test-private-methods-with-dunit)

## 入れ子関数（ネストルーチン）
> 関数や手続きのブロックのローカル宣言セクション内に、別の関数や手続きが含まれる場合もあります。
[参照元URL](https://docwiki.embarcadero.com/RADStudio/Sydney/ja/%E6%89%8B%E7%B6%9A%E3%81%8D%E3%81%A8%E9%96%A2%E6%95%B0%EF%BC%88Delphi%EF%BC%89)

ラムダ式が市民権を得て欲しいな。
```pascal
procedure DoSomething(S: string);
 var
   X, Y: Integer;

   procedure NestedProc(S: string);
   begin
   ...
   end;

 begin
   ...
   NestedProc(S);
   ...
 end;
```
## Assigned vs <> nil
以下のサイトが参考になった
- [Assigned vs <> nil - Stack Overflow](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/167027/aa509904-6d09-fe7e-1d36-0bf22f3af1cc.png)

## High,Low関数
以下のサイトが参考になった。なるほど、DelphiはC#と違って配列が必ずしも「0」始まりではないため、工夫が必要になるのか。
- [C# equivalent to Delphi High() and Low() functions for arrays that maintains performance? - Stack Overflow](https://stackoverflow.com/questions/15602626/c-sharp-equivalent-to-delphi-high-and-low-functions-for-arrays-that-maintain)

## その他
~~細かく書くほどの知識ないので、その他でまとめる~~
- Record型
- ポインタ型
- with句

# IDE(RAD Studio)の設定や使い方
## キーの割り当てについて
RAD Studio用のショートカット覚えるのしんどいですよね... そこで、[キーの割り当て]-[キー割り当てモジュール]から[Visual Studio(TM)エミュレーション]を選択すれば、Visual Studioと同じ感じのショートカットを実現できます。ただ、完璧というわけではなく、以下のショートカットは使えんなという認識です。
※[このサイト](https://docwiki.embarcadero.com/RADStudio/Sydney/ja/Visual_Studio_%E3%82%AD%E3%83%BC%E3%83%9C%E3%83%BC%E3%83%89_%E3%82%B7%E3%83%A7%E3%83%BC%E3%83%88%E3%82%AB%E3%83%83%E3%83%88)に詳しいこと書いてありました。

|機能  |Visual Studioのキー |代替キー　|
|---|---|---|
|コメントの解除  |Ctrl + K + U  |Ctrl + K + C　 |
|行削除  |Ctrl + L  |Ctrl + Y　 |
|変数（関数）の参照検索  |Shift + F12  |Ctrl + Shift + Enter　 |
|参照先への移動  |F12  |Ctrl + クリック　 |
|ユニットやFormの検索  |Ctrl + ,  |Ctrl + F12(ユニット検索) <br> Shift + F12(Form検索)　 |
|ソースコードの整形  |Ctrl + K + D  |Ctrl + D　 |
|フォーム/ユニットの切替え  |F7  |F12　 |
|やり直し  |Ctrl + Y  |Alt+Shift+Backspace　 |

よく使うショートカットものっけます。
|機能  | ショートカット　|
|---|---|
|dfmのコードを確認  |Alt + F12　 |
|クラス補完  |Ctrl + Shift+C　 |
|宣言部/実装部へ移動  |Ctrl + Shift+↑<br>Ctrl + Shift+↓ 　 |
|リファクタリング(変数名の変更)  |Ctrl + Shift + E 　 |

### 参考
- [[Delphi] RAD Studio IDE ショートカット チートシート](https://qiita.com/pik/items/7d57ba02d4a72a88f33f)
- [Delphi IDE の便利な機能 - キーボードショートカットなど](https://qiita.com/CYonezawa/items/ca2c4414cf45bbed1283)

## ウォッチ式について
Visual Studioでのデバッグ時、ウォッチ式やイミディエイトウィンドウを利用すると開発がはかどりますよね。同様の機能を「Ctrl + F2」で[評価/変更]画面を開くことで実現できます。

## コード補完について
[支援機能](https://docwiki.embarcadero.com/RADStudio/Rio/ja/%EF%BC%BB%E6%94%AF%E6%8F%B4%E6%A9%9F%E8%83%BD%EF%BC%BD)に詳しいことが書いてあります。
- **[予約語の表示]** は早いうちから設定しておくべきだった...
- Visual Studioと同様、[Ctrl + Space]や[Ctrl + Shift + Space]といったショートカットは使える

## エディタフォントについて
**Consolas** でいきましょう！目に優しいフォントですし、「O(おー)」と「0(ゼロ)」の区別もつきやすいです。英語版のVisual StudioやDelphi11では当フォントがデフォです。デフォの文字サイズは気持ち小さいので「12」くらいまで大きくしてみるといいかも。

## ダークテーマの適用
[Delphi IDE Theme Editor](https://github.com/RRUZ/delphi-ide-theme-editor)が使えるならそれでヨシ！また、Delphi 10.2 Tokyoからデフォで設定可能になります。↑のツールがダウンロードできない場合、[このサイト](https://github.com/RWarnecke/Delphi-Editor-Theme)からレジストリをコピーして適用すればOK。

## IDEで使用するフォントの変更
エディタフォントではなく、その他のGUI部分のフォントの変更方法です。以下をメモ帳とかに書いてダブルクリックすれば適用されます。Delphi XE8くらいから使えるっぽい。Delphiのバージョン番号は適宜修正お願いします。
```
Windows Registry Editor Version 5.00

[HKEY_CURRENT_USER\SOFTWARE\Embarcadero\BDS\19.0\ModernTheme]
"FontName"="源ノ角ゴシック Bold"
"FontSize"=dword:00000009
"MainToolBarColor"="$00EAD1B9"
```
### Delphiのレジストリバージョンまでの番号
備忘のためメモメモ
| 番号  |  Delphiのバージョン                  |
| -- | -------------------------- |
| 5  | Delphi 5                  |
| 6  | Delphi 6                  |
| 7  | Delphi 7                  |
| 2  | Delphi 8                  |
| 3  | BDS 2005                  |
| 4  | BDS 2006                  |
| 5  | RAD Studio 2007           |
| 6  | RAD Studio 2009           |
| 7  | RAD Studio 2010           |
| 8  | RAD Studio XE             |
| 9  | RAD Studio XE2            |
| 10 | RAD Studio XE3             |
| 11 | RAD Studio XE4             |
| 12 | RAD Studio XE5             |
| 13 | Appmethod 1.13             |
| 14 | RAD Studio XE6             |
| 15 | RAD Studio XE7             |
| 16 | RAD Studio XE8             |
| 17 | RAD Studio 10 Seattle      |
| 18 | RAD Studio 10.1 Berlin     |
| 19 | RAD Studio 10.2 Tokyo      |
| 20 | RAD Studio 10.3 Rio        |
| 21 | RAD Studio 10.4 Sydney     |
| 22 | RAD Studio 11.0 Alexandria |

### 参考
- [RAD Studio の IDE で使用するフォントをレジストリを書き換えて変更する](https://pslabo.hatenablog.com/entry/2016/07/15/RAD_Studio_%E3%81%AE_IDE_%E3%81%A7%E4%BD%BF%E7%94%A8%E3%81%99%E3%82%8B%E3%83%95%E3%82%A9%E3%83%B3%E3%83%88%E3%82%92%E3%83%AC%E3%82%B8%E3%82%B9%E3%83%88%E3%83%AA%E3%82%92%E6%9B%B8%E3%81%8D%E6%8F%9B)
- [Delphi/C++Builder/RAD StudioのIDE画面のフォントを差し替えて見やすくしてみよう](https://qiita.com/kazinoue/items/424c6e042a6382f9c085)

# Delphiの開発で使う各種技術(フレームワークやDBなど)

## DBMS
DBMSはDelphiやC#といった言語に依存しないです。Delphiで使われがちな技術を解説しませう。
|機能  |補足 |
|---|---|
|Paradox    |古の時代より使われている()embarcadero製のRDBMS |
|InterBase  |embarcadero製のRDBMS  |
|Firebird   |InterBase6をもとに開発されたRDBMS  |
|SQL Server |C#erもおなじみ、MS製のRDBMS  |

## DBプロバイダ
DBプロバイダはどちらかというと、OSといったプラットフォームに依存します。C#でもDBプロバイダ経由でDBにアクセスします(あたりまえ)。Delphiで使われがちな技術を解説しませう。
|機能  |補足 |
|---|---|
|ODBC   |MS謹製。様々なDBとのやり取り方法を統一するための規約・共通のインターフェイス  |
|OLE DB |MS謹製。ODBCをより抽象化し、RDB以外へのデータアクセスもできるようにした  |
|ADO　  |MS謹製。OLEDBを利用して、さまざまなデータソースへアクセスする  |

## データベースクライアントAPI
C#でいうところのADO.NETやEntity Frameworkに相当します。機能は遠く及びませんが...
|機能  |
|---|
|BDE                |
|dbGO(ADO Express)  |
|FireDAC            |

## UIフレームワーク
C#でいうところのWin FormsやWPF、UWPなどに相当します。機能は(ry
|機能  |
|---|
|VCL       |
|FireMonkey |

## WEB技術
C#でいうところのASP.NETなどに相当します。機能は(ry
|機能  |補足 |
|---|---|
|Indy     | - |
|DataSnap |C/Sアプリを作成するのに利用可能な、Delphi技術。TCP/IP、HTTPでJSONデータをクライアント/サーバ間でやり取りする手段を提供する  |

# コンパイルの仕組み
## コンパイラ
Delphiのバージョン次第だが、C#は「csc.exe」で、Delphiは「DCC32.EXE」でコンパイルされる。

## ビルド
こちらもバージョン次第だが、C#とDelphiともに「MSBuild.exe」でビルドされる。コンパイラはDelphiのものを使うとのことなので、インストールは別途必要そう。

## 動きの違い
C#でcsc.exeを実行すると、EXEファイルが出力される。
DelphiはDCC32.EXEを実行すると、dcuファイルが出力される。MsBuild.exeがdcuファイルをかき集めてEXEファイルを出力する。

## 参考
- コンパイルとは？
    - https://twitter.com/tadsan/status/1471888871223066626
- Delphiとコンパイル
    - [How to compile and run this Delphi code without installing an IDE?](https://stackoverflow.com/questions/1986011/how-to-compile-and-run-this-delphi-code-without-installing-an-ide)

# オープンソースを読もう！
Delphiのコードを本来どう書くべきか分からなくなる。そんな時は、[Awesome Delphi](https://github.com/synopse/awesome-delphi)や[Githubのトレンド](https://github.com/trending/pascal)内の気になるソースを漁るのはおススメと思う。

個人的にで読んでおもしろかったソースを紹介します。
- [delphi-ide-theme-editor](https://github.com/RRUZ/delphi-ide-theme-editor)
- [menialtasks](https://github.com/malcolmgroves/menialtasks)
- [Robber](https://github.com/MojtabaTajik/Robber)
- [NVMe Tools](https://github.com/ebangin127/nvmetools)
- [DSharp](https://bitbucket.org/sglienke/dsharp/src/master/)
- [Delphi-Mocks](https://github.com/VSoftTechnologies/Delphi-Mocks)
- [DUnitX](https://github.com/VSoftTechnologies/DUnitX)
- [Spring4D](https://bitbucket.org/sglienke/spring4d/src/master/)

# お勉強用の資料を紹介
## [Delphi / C++Builder Starter チュートリアルシリーズ](http://forms.embarcadero.com/starter-tutorial-webinar)
Delphiの書き方よく分からない😵‍💫 、文法から分からない人にオススメしたい内容になってます。文法が分かってる人も再確認になっていいかも。動画は[このリンク](https://www.youtube.com/watch?v=r2K-1XR37WA&list=PLoQxxVNY10oEmNSjiPdYPV_E9IL9ipico&index=2)から見れますので、紹介しときます。

## [開発者が知りたい実践プログラミングテクニック！](https://www.migaro.co.jp/contents/support/technical_seminar_search/21st/Session4.pdf)
効果的なデバッグの方法が紹介されている資料です。

## [Embarcadero White Paper](https://www.embarcadero.com/resources/white-papers/?dmy=true)
フォームに情報を入力すれば、無料でe-Bookを取得できます(どれも英語ですが...)。オススメと本の概要は↓

### [Coding in Delphi](https://lp.embarcadero.com/CodinginDelphi)
例外の扱い方、ジェネリクスや匿名関数、インターフェースRTTIの使い方といった、中級~くらいの文法が紹介されているイメージ。ユニットテストの書き方に関する説明もあり、非常に重宝している。基本的な文法の説明は端折られてるため、初心者にはオススメしない本かなという印象。

### [Object Pascal Handbook Delphi 11 Alexandria Edition](https://lp.embarcadero.com/ObjectPascalHandbookD11)
邦訳もされてる[あの鈍器](https://www.amazon.co.jp/OBJECT-PASCAL-HANDBOOK-Delphi-Alexandria%E3%81%AE%E3%81%9F%E3%82%81%E3%81%AEObject/dp/4877835210)。英語版なら無料で手に入るみたい。Object Pascalの文法が基本的なところから書かれている。なんとなくコード書けちゃってるが、文法よく分かってない人に向いてる本かも。
というか、「Delphi」と「Object Pascal」って違うのか。Delphi言語なるものはもう存在しない事実を最近知った([参考](https://qiita.com/pik/items/c34ca15bffc8f09127e6))。

### [Code Faster in Delphi](https://lp.embarcadero.com/CodeFasterinDelphi)
IDEの効率的な使い方が紹介されている。やっぱり、もっと効率的な開発手法ありそうだなぁーと考えさせられる。たとえば、[Sync Edit(同期編集)](https://docwiki.embarcadero.com/RADStudio/Alexandria/ja/%E5%90%8C%E6%9C%9F%E7%B7%A8%E9%9B%86%EF%BC%88IDE_%E3%83%81%E3%83%A5%E3%83%BC%E3%83%88%E3%83%AA%E3%82%A2%E3%83%AB%EF%BC%89)とか。頭のいい人がどんな開発環境で開発してるか垣間見ることができてオススメ。

### [More Coding in Delphi](https://lp.embarcadero.com/MoreCodinginDelphi)
文法というより、Delphiの設計に関する本。設計についてまとまったDelphiの本、はじめて見た💦
SOLID原則や、GoFのデザインパターンといったオブジェクト指向をDelphiでどのように実装するか紹介されてます。

### [Dependency Injection in Delphi](https://lp.embarcadero.com/DependencyInjection)
書名のとおり、依存性の注入パターンの説明からはじまり、Delphiでの実装方法がStep-By-Stepで紹介されています。

## [エンバカデロ・デベロッパーキャンプのアーカイブ](https://www.embarcadero.com/jp/events-japan/developer-camp/archive)
Delphiの文法やRAD Studioの使い方、フレームワーク(DataSnap、FireDAC、VCL、Fire Monkeyとかとか)に関する資料が豊富に掲載されてます。役立ちそうな資料は別途まとめたい。

## [エンバカデロ・テクノロジーズ(YouTube)](https://www.youtube.com/user/EmbarcaderoTechJapan)
月一で「エンバカデロ・デベロッパーTV」が更新されます。Delphiにまつわるホットな話題が紹介されますので、技術的な話題にキャッチアップできるかも!?

## [Delphi-PRAXiS](https://www.delphipraxis.net/forum.php)
Delphiの掲示板。ドイツ語だが、情報量はスゴイ！

## [Inside VCL](http://tknakamuri.web.fc2.com/invcl.htm)
VCLの仕組みに関する知識がまとまって紹介されてる。

# その他
## Delphi XEの「XE」は「Crossplatform Edition」の略
なるほど、当時のC#はほぼWindowsでしか動かない状態だったのでクロスプラットフォームは大きなセールスポイントだったんですね。Monoとか懐かしい。いまや、XamarinやMAUIの登場でウマミが徐々になくなってる感じですね。
- [Delphi 言語に見る顕在化する言語のリスクとは？](https://www.slideshare.net/pik256/llf-25562697)
- [History of Delphi — from Pascal to Embarcadero Delphi XE 2](https://vakrio.medium.com/history-of-delphi-from-pascal-to-embarcadero-delphi-xe-2-c6809366ae45)

# 開発してて辛いこと
ただの愚痴です...でも、共感できる人は多いはず。

## サンプルコードが少ない
実装してて一番辛いのはこれに尽きます。たとえば、イミュータブルなクラスを作りたいと思い書き方を検索してもロクなサイトが出てきません。Delphiでドメイン駆動設計のサンプルコードをGitHubなどから検索しても見つかりませんでした(探し方の問題かもしれませんが)。DDDに限らず、流行りの設計パターンで実装されたコードも同様に見つからないため、んまぁ使いたいとはならんですよね。

## おまじない多すぎ問題
「implementation」、「type」、「procedure」、「function」、etc.. 単純に'Hello World'を出力するVCLアプリを作るだけでよく分からんおまじないが多すぎて怖いです。この「怖い」という感覚が競技人口を減らす原因なんだなぁーと。C#の場合、最近実装されたGlobal Usingのおかげで、ついぞ'Hello World'を出力する際のおまじないがなくなったんだそうな
- [global using](https://ufcpp.net/blog/2021/11/implicitusings/)

## メモリを開放しなくてはいけない
ガベージコレクション万歳！

## デコンパイルできない
C#の場合、コンパイルすると中間言語(IL)ができ、実行時に.NET FrameworkがILを解釈することで動きます。一方、Delphiはコンパイルすると、より機械語に近い状態(もしくは機械語?)になります。よって、出来上がるものが同じEXEファイルでも性質が異なり、機械語に近いDelphiをデコンパイルするのは困難を極めます。そして機械語に近い分、プログラムの速度はC#より速いといわれます。.NET7でネイティブコンパイルが搭載されることで当メリットもなくなっちゃいますけどね。

**C#よ、頼むからDelphiを駆逐してくれ...**