SE初心者がSwiftでぶち当たった壁について書いてみた。

#はじめに

私は、今年の4月からSEとして働き始めています。
今回は、そんなSE歴半年の私が、Swiftを使っている中でぶち当たった壁について書いてみようと思います。
主なトピックは、以下の3つになります。

①クラス、インスタンスって何なん？
②クラスと構造体はどう使い分けるの？
③カタカナからローマ字に自動変換させる処理ってどう書けばいい？

#① クラスとインスタンスって何なん？
まず、直面した難関がこれです。
文字列、定数と変数、関数などは、文系人間でも割りかし理解しやすい単元だったのですが、
クラスとインスタンスについては結構苦戦を強いられました。
（今でも完全に理解できているかは定かではないですが、、、）

ここからは、自分なりにクラスとインスタンスについて解説してみようと思います。

クラスとインスタンスは、一言でいうと、
**クラスは「設計図」**で、**インスタンスは「その設計図から作成されたモノ」**みたいな感じです。

車を例に挙げて説明してみましょう。

ここに車の設計図があります。
この設計図には、車がもつ共通の仕様（アクセルを踏んだら前に進む、ブレーキを踏んだら止まるなど）が書かれています。
この共通の仕様が記載された設計図がクラスに該当します。

そして、この設計図から実際に作った車がインスタンスに相当します。

なので、あるクラスを使用したいと思ったら一度インスタンス化しないとダメだということですね。
（車の設計図だけあっても、車は使えませんしね。）

#② クラスと構造体はどう使い分けるの？
さらに学習を進めていくと、構造体という概念に出会いました。

構造体はクラスとたくさんの類似点があるということを学んだのですが、
その時、私はふとこう思いました。

「え、じゃあ、どうやって使い分けんの？」と、、、

私が使っていたテキストには、構造体とクラスの違いの説明が割愛されており、
非常に困りました。

ネットで検索しまくった結果、わかりやすいサイトが2つ見つかったので、
これらのサイトを活用しつつ、構造体とクラスの違いについて説明していきたいと思います。
[Swiftで構造体とクラスを使い分ける方法(ポイント)](https://swift.tecc0.com/?p=289)
[【swift】イラストで分かる！classとstructの違いについて【初心者向け】](https://qiita.com/narukun/items/24d9e68ff965f8da09ad)

違いは主に2点あります。

**1つ目は、継承できるかどうかという点です。**
継承とは、あるクラスの定数や変数、関数など、そのクラスの性質を引き継いで新しいクラスを作ることです。

後々、この継承が必要そうであればクラスを使ったほうがいいということですね。

**2つ目は、クラスは参照型であるが、構造体は値型であるという点です。**
参照型（参照を渡す）と値型（値を渡す）については、上記したサイトを参考にして下さい。

そして、値型である構造体はその性質上、使用するメモリが増えてしまうので、
データが大きければクラスを使うようにしましょう。

#③ カタカナからローマ字に自動変換させる処理ってどう書けばいい？
あるプロジェクトでこの処理を自力で書く必要があり、結構手こずりました。

悪戦苦闘した結果、完成したコードの抜粋が以下の通りになります。
所々省略しておりますが、その点ご容赦ください😥

```
/// カタカナをローマ字に変換する
    ///
    /// - parameter katakana:        変換対象の文字列（カナ）
    ///
    /// - returns: 変換後の文字列（ローマ字）
    static func kataToRoman(katakana : String) -> String{
        
        var newKatakana = katakana
        
        if katakana.contains("キャ"){
            newKatakana = katakana.replacingOccurrences(of: "キャ", with: "KYA")
        }
        
        if newKatakana.contains("キュ"){
            newKatakana = newKatakana.replacingOccurrences(of: "キュ", with: "KYU")
        }
        
        〜〜〜中略〜〜〜
        
        if newKatakana.contains("ッ"){
            
            var kataArray : [Character] = []
            for kataChar in newKatakana.characters{
                kataArray.append(kataChar)
            }
            
            if kataArray[kataArray.count - 1] == "ッ"{
                kataArray.removeLast()
                newKatakana = String(kataArray) + "TSU"
            }
            
            var newKataArray : [Character] = []
            var kataRomanArray : [Character] = []
            
            for kataRomanChar in newKatakana.characters{
                kataRomanArray.append(kataRomanChar)
            }
            
            var kataRomanIndex = kataRomanArray.index(of: "ッ")
            if kataRomanIndex != nil{
                for var kataRoman in kataRomanArray.reversed(){
                    if kataRoman == "ッ"{
                        kataRoman = newKataArray[newKataArray.count - 1]
                    }
                    newKataArray.append(kataRoman)
                }
                newKatakana = String(newKataArray.reversed())
            }
        }
        
        //自動変換されたローマ字からローマ字以外の文字を除く
        let regex = try! NSRegularExpression(pattern:"[^A-Z]", options: [])
        let mutableString = NSMutableString(string: newKatakana)
        regex.replaceMatches(in: mutableString, options: [], range: NSRange(location: 0, length: newKatakana.characters.count), withTemplate: "")
        newKatakana = mutableString.description
        
        return newKatakana
    }
}
```

変換ルールは、こちらを参考にしています。
[ヘボン式ローマ字綴方表](https://www.seikatubunka.metro.tokyo.lg.jp/passport/documents/0000000485.html)

また、小文字の「ッ」の変換については、
上のコードで書いたように、少々工夫が必要になるので注意しましょう！

#まとめ
以上、駆け出しSEの私がこれまでにぶつかった壁について書いてみました。
最後までお読みいただき、ありがとうございました！