文字列と文字


string (文字列)は、"hello,world""albatross" などの、文字の一続きです。Swift の文字列は String 型として表現されます。String の内容は Character 値の集合 (collection) を含む、様々な方法でアクセスできます。


Swift の StringCharacter 型は、コード内のテキストを操作するために高速で Unicode 準拠の方法を提供します。文字列の作成と操作のための構文は、C 言語に似ている、文字列リテラル構文で、軽量で、読み取りやすいです。文字列の連結は、簡単で、+ 演算子で二つの文字列を一緒に結合し、文字列の可変性は、定数または変数を選択することによって管理され、Swift の他の値と同じです。文字列を使用して、定数、変数、リテラル、および式を、より長い文字列に挿入することもでき、文字列補間のプロセスとして知られています。これにより、表示、保存、および印刷用のカスタム文字列値を簡単に作成できます。


構文のこの単純さにもかかわらず、Swift の String 型は、高速で、現代的な文字列の実装を行なっています。すべての文字列は、コード化に依存しない Unicode 文字で構成されており、様々な Unicode の表現でこれらの文字にアクセスするためのサポートを提供しています。


注意: Swift の String 型は、Foundation の NSString のクラスにブリッジされます。Foundation はまた、NSString で定義されたメソッドを公開するため String を拡張します。これは、Foundation を import する場合は、キャストする事なく、String 上でこれらの NSString のメソッドにアクセスすることができる事を意味します。


Foundation と Cocoa で String を使用する方法の詳細については、ココアと Objective-C で Swift を使用する(Swift 4) 内の ココアのデータ型を使用した作業 を参照してください。




文字列リテラル


文字列リテラル としてコード内で事前に定義された String 値を含めることができます。文字列リテラルは、二重引用符(")で囲まれた文字のシーケンスです。


定数または変数の初期値として文字列リテラルを使用して下さい。


let someString = "Some string literal value"


文字列リテラル値で初期化されているので、Swift は someString 定数が String の型であると推測することに注意してください。


複数行の文字列リテラル


複数の行にまたがる文字列が必要な場合は、複数行の文字列リテラルを使用して下さい。文字のシークエンスは 3 つの二重引用符で囲みます。


  1. let quotation = """
  2. The White Rabbit put on his spectacles. "Where shall I begin,
  3. please your Majesty?" he asked.
  4. "Begin at the beginning," the King said gravely, "and go on
  5. till you come to the end; then stop."
  6. """


複数行の文字列リテラルには、その前後の引用符の間にあるすべての行が含まれます。文字列は開始引用符 (""") の後の最初の行で始まり、終了引用符の前の行で終わります。つまり、開始前または改行で終了したいずれの文字列でもない事を意味します。


  1. let singleLineString = "These are the same."
  2. let multilineString = """
  3. These are the same.
  4. """


ソースコードに複数行の文字列リテラル内に改行が含まれる場合、その改行も文字列の値に表示されます。改行を使用してソースコードを読みやすくすしたい場合、でも改行を文字列の値の一部にしたくない場合は、行末にバックスラッシュ(\)を記述して下さい。


  1. let softWrappedQuotation = """
  2. The White Rabbit put on his spectacles. "Where shall I begin, \
  3. please your Majesty?" he asked.
  4. "Begin at the beginning," the King said gravely, "and go on \
  5. till you come to the end; then stop."
  6. """


改行で始まる行または終わる複数行の文字列リテラルを作成するには、空白行を最初または最後の行として記述します。例えば:


  1. let lineBreaks = """
  2. This string starts with a line break.
  3. It also ends with a line break.
  4. """


複数行の文字列は、周囲のコードに合わせてインデントすることができます。閉じ引用符 (""") の前の空白は、Swift に他のすべての行の前に無視すべき空白を示します。しかし、空白を囲み引用符の前にあるものに加えて行頭に空白を書き込むと、その空白が含まれます。


multilineStringWhitespace_2x


上記の例では、複数行の文字列リテラル全体がインデントされていても、文字列の最初と最後の行は空白で始まりません。中間の行は終わりの引用よりもインデントが多いので、余分な 4 つの空白のインデントで始まります。


文字列リテラル内の特殊文字


文字列リテラルには、以下の特殊文字を含めることができます。


以下のコードは、これらの特殊文字の 4 つの例を示しています。wiseWords 定数には、2 つのエスケープした二重引用符が含まれています。dollarSignblackHeart、およびsparklingHeart 定数は、Unicode スカラー形式を示しています。


  1. let wiseWords = "\"Imagination is more important than knowledge\" - Einstein"
  2. // "Imagination is more important than knowledge" - Einstein
  3. let dollarSign = "\u{24}"             // $, Unicode scalar U+0024
  4. let blackHeart = "\u{2665}"         // ♥, Unicode scalar U+2665
  5. let sparklingHeart = "\u{1F496}" // 💖, Unicode scalar U+1F496


複数行の文字列リテラルは、1 つではなく 3 つの二重引用符を使用するため、複数行の文字列リテラルの中にエスケープしないで、二重引用符 (") を含めることができます。複数行の文字列に """ を含めるには、引用符の少なくとも 1 つをエスケープします。たとえば、以下のようにします。


  1. let threeDoubleQuotes = """
  2. Escaping the first quote \"""
  3. Escaping all three quotes \"\"\"
  4. """


空の文字列の初期化


長い文字列をビルドするための出発点として空の String 値を作成するには、変数に空の文字列リテラルを代入するか、イニシャライザの構文を使用して新しい String インスタンスを初期化するかのいずれかをします:


  1. var emptyString = ""                         // empty string literal
  2. var anotherEmptyString = String()    // initializer syntax
  3. // these two strings are both empty, and are equivalent to each other


そのブール型の isEmpty プロパティをチェックして、String 値が、空であるかどうかを調べます。


  1. if emptyString.isEmpty {
  2.        print("Nothing to see here")
  3. }
  4. // prints "Nothing to see here"


文字列の可変性


特定の String が変更可能で(又は 変異可能 で) 変数に代入可能か(この場合変更可能)、定数に割り当てられるか(この場合変更不可能)を示します。


  1. var variableString = "Horse"
  2. variableString += " and carriage"
  3. // variableString is now "Horse and carriage"
  4. let constantString = "Highlander"
  5. constantString += " and another Highlander"
  6. // this reports a compile-time error - a constant string cannot be modified


注意: このアプローチは、Objective-C と Cocoa の、文字列が変更可能かどうかを示すために、二つのクラス(NSStringNSMutableString)の間で選択して、文字列可変性を示す事とは異なります。


文字列は値の型


Swift のString 型は 値の型 です。新しい String 値を作成する場合、それが関数やメソッドに渡された時、またはそれはが定数または変数に代入された時、その String 値は コピー されます。それぞれの場合、既存の String 値の新しいコピーが作成され、元のバージョンではなく、新しいコピーが渡されるかが代入されます。値の型についての詳細は、構造体と列挙型は値の型 に記載されています。


Swift のデフォルトでコピーされる String の動作は、関数やメソッドが、String 値を渡すとき、それがどこから来たのかは関係なく、その正確な String 値を所有することを保証します。それをあなた自分が変更しない限り、渡された文字列は変更されないことを確信できます。


舞台裏では、絶対に必要な時だけ実際のコピーが起き、Swift のコンパイラは、文字列の使用を最適化します。これは値型として文字列を扱うときは、常に素晴らしいパフォーマンスを得られることを意味します。



文字を使った作業


その文字列を for-in ループで反復処理することによって String の、個々の character の値にアクセスすることができます:


  1. for character in "Dog!🐶" {
  2.        print(character)
  3. }
  4. // D
  5. // o
  6. // g
  7. // !
  8. // 🐶


fot-in ループは、For-In ループ の中で説明されています。


代わりに、Character 型注釈を提供することによって、1文字の文字列リテラルから、スタンドアロンの Character 定数または変数を作成できます。


let exclamationMark: Character = "!"



String 値は、そのイニシャライザへの引数として Character 値の配列を渡すことによって構築できます。


  1. let catCharacters: [Character] = ["C", "a", "t", "!", "🐱"]
  2. let catString = String(catCharacters)
  3. print(catString)
  4. // prints "Cat!🐱"


文字列と文字を連結


String 値は新しい String 値を作成するのに、加算演算子(+)で一緒に追加( 連結 )することができます:


  1. let string1 = "hello"
  2. let string2 = " there"
  3. var welcome = string1 + string2
  4. // welcome now equals "hello there"


また、加算代入演算子(+=)で既存の String 変数に String 値を追加できます:


  1. var instruction = "look over"
  2. instruction += string2
  3. // instruction now equals "look over there"


String 型の append() メソッドを持つ String 変数に Character 値を追加できます。


  1. let exclamationMark: Character = "!"
  2. welcome.append(exclamationMark)
  3. // welcome now equals "hello there!"


注意: Character 値は、単一の文字しか含められないため、既存の Character 変数に String または Character を追加することはできません。


複数行の文字列リテラルを使用して長い文字列の行を構築している場合は、最後の行を含め、文字列のすべての行を改行で終わらせます。例えば:


  1. let badStart = """
  2. one
  3. two
  4. """
  5. let end = """
  6. three
  7. """
  8. print(badStart + end)
  9. // Prints two lines:
  10. // one
  11. // twothree
  12. let goodStart = """
  13. one
  14. two
  15. """
  16. print(goodStart + end)
  17. // Prints three lines:
  18. // one
  19. // two
  20. // three


上記のコードでは、badStartend と連結すると 2 行の文字列が生成されますが、これは望んだ結果ではありません。badStart の最後の行は改行で終わらないので、その行は end の最初の行と結合してしまいます。対照的に、goodStart の両方の行は改行で終了しており、したがって end と組み合わせると、結果は望んだとおり、3 行になります。


文字列補間


文字列補間 は、文字列リテラルの中に定数、変数、リテラル、及び式の混合から、それらの値を含める事により、新しい String 値を構築する方法です。単一の行と複数の行の文字列リテラルの両方で文字列補間を使用できます。文字列リテラルに挿入する各項目は、バックスラッシュ (\) を前に付けた括弧で囲みます。


  1. let multiplier = 3
  2. let message = "\(multiplier) times 2.5 is \(Double(multiplier) * 2.5)"
  3. // message is "3 times 2.5 is 7.5"


上記の例では、multiplier の値は \(multiplier) のように文字列リテラル内に挿入されています。文字列補間が実際の文字列を作成するために評価される時、このプレースホルダは、multiplier の実際の値に置き換えられます。


multiplier の値も、文字列の後の大きい式の一部です。この式は、Double(multiplier) * 2.5 の値を計算し、文字列に結果(7.5)を挿入します。この場合は、式は、文字列リテラルの内側に含まれており、\(Double(multiplier) * 2.5) と書かれます。



注意: 補間された文字列の括弧の中の式にははエスケープされていないバックスラッシュ(\) を含めることはできません。また、キャリッジリターンまたはラインフィードを含めることはできません。しかし、それらは他の文字列リテラルを含められます。


ユニコード(Unicode)


ユニコード は異なる書記体系でのコード化、表現、およびテキスト処理のための国際規格です。それは標準化された形式での全ての言語からの、ほぼ全ての文字を表現する事を可能にし、テキストファイルや Web ページのような外部ソースでそれらの文字を読み書きすることができます。このセクションで説明するように Swift の StringCharacter 型は、Unicode に完全に準拠しています。



Unicode スカラー


舞台裏では、Swift 固有の String 型は Unicode スカラー 値からビルドされます。Unicode スカラーは、LATIN SMALL LETTER A ("a") の U+0061 や、または FRONT-FACING BABY CHICK ("🐥") の U+1F425 のような文字や修飾のユニークな 21 ビットの数値です。



注意: Unicode スカラーは U+0000 から U+D7FF まで、または U+E000 から U+10FFFF までを含む範囲の任意の Unicode コードポイント です。Unicode スカラーは、U+D800 から U+DFFF の範囲のコードポイントである Unicode の 代理ペアコード ポイントを含みません。


21 ビットの Unicode スカラーの全てが文字に割り当てられているわけではないことに注意してくださいーいくつかののスカラーは、将来の割り当てのために予約されています。上記の例では文字に割り当てられているスカラーは、典型的には LATIN SMALL LETTER A や、FRONT-FACING BABY CHICK、のように、名前も持っています。


拡張書記クラスタ


Swift の Character 型のすべてのインスタンスは単一の 拡張書記クラスタ を表します。拡張書記クラスタは、(組み合わせた時)単一の、人間が読める文字を生成する 1 つ以上の Unicode スカラーのシーケンスです。


ここで例です。文字 é は、単一の Unicode スカラー(LATIN SMALL LETTER E WITH ACUTE, または U+00E9) é として表わすことができます。ただし、同じ文字がまた COMBINING ACUTE ACCENT スカラー(U+0301)が続く標準の文字 e(LATIN SMALL LETTER E、または U+0065) のスカラーの ペア として表すこともできます。COMBINING ACUTE ACCENT スカラーは、Unicode 対応のテキストレンダリングシステムによってレンダリングされる時、e を 回して é として、それに先行するスカラーにグラフィカルに適用されます。


どちらの場合も、文字 é は、拡張書記クラスタを表す単一の Swift の Character 値として表されます。最初の場合は、クラスタは単一のスカラを含んでおり、第二の場合は、2つのスカラーのクラスタです。


  1. let eAcute: Character = "\u{E9}"                                 // é
  2. let combinedEAcute: Character = "\u{65}\u{301}"        // e followed by ́
  3. // eAcute is é, combinedEAcute is é


拡張書記クラスタは、単一の Character 値として多くの複雑なスクリプト文字を表現するための柔軟な方法です。たとえば、韓国語のアルファベットからのハングルの音節は、合成済みかまたは分解されたシーケンスとして表すことができます。これらの表現の両方が Swift の単一の Character 値としての資格があります:


  1. let precomposed: Character = "\u{D55C}"                               // 한
  2. let decomposed: Character = "\u{1112}\u{1161}\u{11AB}"   // ᄒ, ᅡ, ᆫ
  3. // precomposed is 한, decomposed is 한


拡張書記クラスタは、単一の Character 値の一部として他の Unicode スカラーを囲むように(COMBINING ENCLOSING CIRCLEU+20DD のように) マークを囲むスカラーを有効にします。


  1. let enclosedEAcute: Character = "\u{E9}\u{20DD}"
  2. // enclosedEAcute is é⃝


地域のインジケータ記号の Unicode スカラーは、REGIONAL INDICATOR SYMBOL LETTER U (U+1F1FA) や、REGIONAL INDICATOR SYMBOL LETTER S (U+1F1F8)の組み合わせのような単一の Character 値を作るためにペアで組み合わされます。


  1. let regionalIndicatorForUS: Character = \u{1F1FA}\u{1F1F8}"
  2. // regionalIndicatorForUS is 🇺🇸


文字を数える


文字列内の Character 値のカウントを取得するには、文字列の count プロパティを使用して下さい。


  1. let unusualMenagerie = "Koala 🐨, Snail 🐌, Penguin 🐧, Dromedary 🐪"
  2. print("unusualMenagerie has \(unusualMenagerie.count) characters")
  3. // prints "unusualMenagerie has 40 characters"


Characer 値の拡張書記クラスタを Swift が使うのは、その文字列の連結を意味し、修正が常には文字列の文字数に影響を与えないことに注意してください。


例えば、4文字の単語の cafe で新しい文字列を初期化し、その後で、文字列の最後に COMBINING ACUTE ACCENT(U+0301) を追加すると、結果の文字列はまだ 4 文字の count を持ち、4番めの文字は é であり、e ではありません。:


  1. var word = "cafe"
  2. print("the number of characters in \(word) is \(word.count)")
  3. // prints "the number of characters in cafe is 4"
  4. word += "\u{301}"        // COMBINING ACUTE ACCENT, U+0301
  5. print("the number of characters in \(word) is \(word.count)")
  6. // prints "the number of characters in café is 4"


注意: 拡張書記クラスタは、複数の Unicode スカラーで構成されます。これは、異なる文字、そして同じ文字の異なる表現が、保存のため異なる量のメモリを必要とすることを意味します。このため、Swift 内の文字は文字列の表現内で各々同じ量のメモリを消費することはありません。その結果、文字列の文字数は、その拡張書記クラスタ境界を決定するために、文字列を反復することなく計算することはできません。特に長い文字列値を扱う場合は、その文字列の文字数を決定するために count プロパティが文字列全体の Unicode スカラーに対して反復処理する必要があることに注意してください。

count プロパティーによって返される文字の count は、同じ文字を含む NSStringlength プロパティと常に同じではありません。NSString の長さは、文字列の UTF-16 表現内の 16 ビットコード単位の数に基づいており、文字列内の Unicode 拡張書記クラスタの数ではありません。


文字列のアクセスと変更


そのメソッドとプロパティを介して、または添え字付きの構文を使用して文字列にアクセスし、変更します。



文字列のインデックス


String 値には、関連付けられた インデックス型 である、String.Index があります。これは、文字列内の各 Character の位置に対応します。


前述したように、異なる文字数は、保存するのに異なる量のメモリを必要とするため、特定の位置にある Character を決定するためには、その String の開始または終りから各 Unicode スカラーを繰り返し処理しなければなりません。このような理由から、Swift の文字列は整数値によってインデックス付けすることはできません。


String の最初の Character の位置にアクセスするため startIndex プロパティを使用して下さい。endIndex のプロパティは、String の最後の文字の直後の位置です。その結果、endIndex プロパティは、文字列の添字への有効な引数ではありません。String が空の場合、startIndexendIndex は等しくなります。


指定されたインデックスの前後にあるインデックスにアクセスするには、Stringindex(before:) および index(after:) メソッドを使用して下さい。指定されたインデックスから離れたインデックスにアクセスするには、これらのメソッドの 1 つを複数回呼び出すのではなく、index(_:offsetBy:) メソッドを使用できます。


添字構文を使用して、特定の String インデックスの Character にアクセスできます。


  1. let greeting = "Guten Tag!"
  2. greeting[greeting.startIndex]
  3. // G
  4. greeting[greeting.index(before: greeting.endIndex)]
  5. // !
  6. greeting[greeting.index(after: greeting.startIndex)]
  7. // u
  8. let index = greeting.index(greeting.startIndex, offsetBy: 7)
  9. greeting[index]
  10. // a


文字列の範囲外のインデックスで文字列の範囲や Character の外側のインデックスにアクセスしようとすると、実行時エラーが引き起こされます。


  1. greeting[greeting.endIndex] // error
  2. greeting.index(after: endIndex) // error


文字列内の個々の文字の全てのインデックスにアクセスするために indices プロパティーを使用して下さい。



  1. for index in greeting.indices {
  2.         print("\(greeting[index]) ", terminator: "")
  3. }
  4. // prints "G u t e n T a g"


注意: Collection プロトコルに準拠している全ての型で、startIndexendIndex プロパティー、そして index(before:)、index(after:)、及び index(_:offsetBy:) メソッドを使用できます。これには、ここに示すように StringArrayDictionarySet などのコレクション型が含まれます。


挿入と削除


指定されたインデックス位置で、文字列に単一の文字を挿入するには、insert(_:at:) メソッドを使用し、指定されたインデックス位置に別の文字列の内容を挿入するには、insert(contentsOf:at:) を使用して下さい。


  1. var welcome = "hello"
  2. welcome.insert("!", at: welcome.endIndex)
  3. // welcome now equals "hello!"
  4. welcome.insert(contentsOf: " there", at: welcome.index(before: welcome.endIndex))
  5. // welcome now equals "hello there!"


指定されたインデックスにある文字列から単一の文字を削除するには、remove(at:) メソッドを使用し、また指定された範囲にある部分文字列を削除するには、removeSubrange(_:) メソッドを使用して下さい。


  1. welcome.remove(at: welcome.index(before: welcome.endIndex))
  2. // welcome now equals "hello there"
  3. let range = welcome.index(welcome.endIndex, offsetBy: -6)..<welcome.endIndex
  4. welcome.removeSubrange(range)
  5. // welcome now equals "hello"


注意: insert(_:at:), insert(contentsOf:at:), remove(at:),及び removeSubrange(_:) メソッドをRangeReplaceableCollection プロトコルに準拠する全ての型で使用できます。これはここで示したように String を含み、 Array,Dictionary,及び Set のようなコレクション型も含みます。


部分文字列


たとえば、添え字や prefix(_:) のようなメソッドを使用して、文字列から部分文字列を取得すると、結果は別の文字列ではなく Substring のインスタンスになります。Swift の部分文字列には文字列とほとんど同じメソッドがあります。つまり、文字列の場合と同じ方法で部分文字列を処理できます。ただし、文字列とは異なり、文字列に対してアクションを実行している間は、短い時間だけ部分文字列を使用します。長い時間結果を格納する準備ができたら、部分文字列を String のインスタンスに変換して下さい。例えば:


  1. let greeting = "Hello, world!"
  2. let index = greeting.index(of: ",") ?? greeting.endIndex
  3. let beginning = greeting[..<index]
  4. // beginning is "Hello"
  5. // Convert the result to a String for long-term storage.
  6. let newString = String(beginning)


文字列と同様に、各部分文字列には、部分文字列を構成する文字が格納されるメモリ領域があります。文字列と部分文字列の違いは、パフォーマンスの最適化として、元の文字列を格納するメモリの一部または別の部分文字列を格納するのに使用されるメモリの一部を部分文字列で再利用できることです。(文字列にも同様の最適化がありますが、2 つの文字列がメモリを共有する場合は同じです。) このパフォーマンスの最適化は、文字列または部分文字列を変更するまでメモリをコピーするパフォーマンスのコストを支払う必要がないことを意味します。前述のように、部分文字列は長期記憶には適していません。というのも元の文字列の記憶域を再利用するため、部分文字列が少しでも使用されている限り元の文字列全体をメモリに保持しなければなりません。


上記の例で言えば、greeting は文字列です。つまり、文字列を構成する文字が格納されているメモリ領域があります。beginninggreeting の部分文字列であるため、greeting が使用するメモリを再利用します。これとは対照的に、newString は文字列です。部分文字列から作成されたときは、独自の記憶域を持ちます。下の図は、これらの関係を示しています。


stringSubstring_2x


注意: StringSubstring の両方とも StringProtocol のプロトコルに準拠しており、これは、文字列操作の関数が StringProtocol 値を受け入れることがしばしば便利であることを意味します。このような関数は、String または Substring のいずれかの値で呼び出すことができます。

文字列の比較


Swift は、テキストの値を比較する3つの方法を提供します:文字列と文字の等価性、接頭句の等価性、接尾辞の等価性。


文字列と文字の等価性


比較演算子 で説明したように、文字列と文字の等価性は、"等価"演算子(==)と"不等価"演算子(!=)でチェックできます。


  1. let quotation = "We're a lot alike, you and I."
  2. let sameQuotation = "We're a lot alike, you and I."
  3. if quotation == sameQuotation {
  4.        print("These two strings are considered equal")
  5. }
  6. // prints "These two strings are considered equal"


それらの拡張書記クラスタが 正式に等価 である場合、2つの String 値(または2つの Character 値)は等しいと見なされます。それらが舞台裏で、異なる Unicode スカラーから構成されている場合でも、同じ言語的意味と外観を持っている場合、拡張書記クラスタは正式に等価です。


例えば、LATIN SMALL LETTER E WITH ACUTE (U+00E9)は LATIN SMALL LETTER E (U+0065)に COMBINING ACUTE ACCENT (U+0301)を組み合わせることと正式に等価です。これら両方の拡張書記クラスタは文字 é を表すための有効な方法であり、従って、それらは正式に等価であると考えられます。


  1. // "Voulez-vous un café?" using LATIN SMALL LETTER E WITH ACUTE
  2. let eAcuteQuestion = "Voulez-vous un caf\u{E9}?"
  3. // "Voulez-vous un café?" using LATIN SMALL LETTER E and COMBINING ACUTE ACCENT
  4. let combinedEAcuteQuestion = "Voulez-vous un caf\u{65}\u{301}?"
  5. if eAcuteQuestion == combinedEAcuteQuestion {
  6.        print("These two strings are considered equal")
  7. }
  8. // prints "These two strings are considered equal"


逆に、英語で使用される LATIN CAPITAL LETTER A(U+0041、または "A")は、ロシアで使用される、CYRILLIC CAPITAL LETTER A (U+0410, または "А")の文字と等価では ありません。文字は、見た目には似ていますが、同じ言語的な意味は持っていません:


  1. let latinCapitalLetterA: Character = "\u{41}"
  2. let cyrillicCapitalLetterA: Character = "\u{0410}"
  3. if latinCapitalLetterA != cyrillicCapitalLetterA {
  4.        print("These two characters are not equivalent")
  5. }
  6. // prints "These two characters are not equivalent"


注意: Swift の文字列と文字の比較はロケールに依存しません。


接頭辞と接尾辞の等価性


文字列が特定の文字列の接頭辞や接尾辞を持っているかどうかをチェックするには、両方とも String 型の単一の引数を取りブール値を返す、文字列の hasPrefix(_:)hasSuffix(_:) メソッドを呼び出します。


以下の例では、シェイクスピアの ロミオとジュリエット の最初の二つの幕から、シーンの場所を表す文字列の配列を考えてみます。


  1. let romeoAndJuliet = [
  2.        "Act 1 Scene 1: Verona, A public place",
  3.        "Act 1 Scene 2: Capulet's mansion",
  4.        "Act 1 Scene 3: A room in Capulet's mansion",
  5.        "Act 1 Scene 4: A street outside Capulet's mansion",
  6.        "Act 1 Scene 5: The Great Hall in Capulet's mansion",
  7.        "Act 2 Scene 1: Outside Capulet's mansion",
  8.        "Act 2 Scene 2: Capulet's orchard",
  9.        "Act 2 Scene 3: Outside Friar Lawrence's cell",
  10.        "Act 2 Scene 4: A street in Verona",
  11.        "Act 2 Scene 5: Capulet's mansion",
  12.        "Act 2 Scene 6: Friar Lawrence's cell"
  13. ]


劇の第 1 幕ではシーンの数をカウントするのに romeoAndJuliet 配列と hasPrefix(_:) メソッドを使用できます。


  1. var act1SceneCount = 0
  2. for scene in romeoAndJuliet {
  3.        if scene.hasPrefix("Act 1 ") {
  4.                 act1SceneCount += 1
  5.        }
  6. }
  7. print("There are \(act1SceneCount) scenes in Act 1")
  8. // prints "There are 5 scenes in Act 1"


同様に、キャピュレット公邸と、修道士ロレンス庵の周囲で行われるシーンの数をカウントするのに hasSuffix(_:) メソッドを使用できます。


  1. var mansionCount = 0
  2. var cellCount = 0
  3. for scene in romeoAndJuliet {
  4.        if scene.hasSuffix("Capulet's mansion") {
  5.                 mansionCount += 1
  6.        } else if scene.hasSuffix("Friar Lawrence's cell") {
  7.                 cellCount += 1
  8.        }
  9. }
  10. print("\(mansionCount) mansion scenes; \(cellCount) cell scenes")
  11. // prints "6 mansion scenes; 2 cell scenes"


注意: 文字列と文字の等価性 で説明したように、hasPrefix(_:)hasSuffix(_:) メソッドは、それぞれの文字列の拡張書記クラスタ間で文字単位の正式な等価比較を行います。


文字列の Unicode 表現


Unicode 文字列は、テキストファイルまたはその他の記憶装置に書き込まれると、その文字列内の Unicode スカラーは、いくつかの Unicode に定義された コード化形式 のいずれか一つでコード化されます。各形式は コード単位 として知られる小さな塊に文字列をコード化します。これらは、UTF-8 コード化形式(これは 8 ビットコード単位として文字列をコード化します)と、UTF-16 コード化形式(これは 16 ビットコード単位として文字列をコード化します)、および UTF-32 符号化形式(これは 32 ビットコード単位として文字列をコード化します)を含みます。


Swift は、文字列の Unicode 表現にアクセスするのに、いくつかの異なる方法を提供します。for-in 文で文字列を反復処理して、Unicode 拡張書記クラスタとしての個々の Character 値にアクセスできます。このプロセスは、文字を使った作業 で説明しました。


その他、3つの他の Unicode 準拠の表現のうちの一つの String 値にアクセスできます。


以下の各例で、D,o.g,‼ (DOUBLE EXCLAMATION MARK、または Unicode スカラー U+203C) の文字で構成されている次の文字列の違った表現、および 🐶 文字(DOG FACE, または Unicode スカラー U+1F436)を示します:


let dogString = "Dog‼🐶"



UTF-8 表現


Stringutf8 プロパティを反復処理することによってその UTF-8 表現にアクセスできます。このプロパティは、String.UTF8View 型で、文字列の UTF-8 表現の各バイトの 1 つは符号なし 8 ビット(UInt8)値であるコレクションです。


UTF8_2x


  1. for codeUnit in dogString.utf8 {
  2.        print("\(codeUnit) ", terminator: "")
  3. }
  4. print("")
  5. // 68 111 103 226 128 188 240 159 144 182


上記の例では、最初の3つの十進の codeUnit 値(68、111、103)は UTF-8 表現がそれらの ASCII 表現と同じ文字 D、o、および g を表します。次の3つの十進の codeUnit 値(226、128、188)は DOUBLE EXCLAMATION MARK 文字の3バイトの UTF-8 表現です。最後の4つの codeUnit 値(240、159、144、182)は、DOG FACE 文字の4バイトの UTF-8 表現です。



UTF-16 表現


文字列の utf16 プロパティを反復処理することによって String の UTF-16 表現にアクセスできます。このプロパティは、String.UTF16View 型で、文字列の UTF-16 表現の各 16 ビットコード単位の一つである符号なしの 16 ビット(UInt16)値のコレクションです。


UTF16_2x


  1. for codeUnit in dogString.utf16 {
  2.        print("\(codeUnit) ")
  3. }
  4. print("\n")
  5. // 68 111 103 8252 55357 56374


もう一度言うと、最初の3つの codeUnit 値(68、111、103)は、その文字の UTF-16 コード単位が、文字列の UTF-8 表現と同じ値を持つ D、o、および g を表します(これらの Unicode スカラーは ASCII 文字を表すため)。


4番目の codeUnit 値(8252)は DOUBLE EXCLAMATION MARK 文字の Unicode スカラー U+203C を表す 16 進値 203C と等しい十進数です。この文字は、UTF-16 の単一のコード単位として表すことができます。


5番目と6番目の codeUnit 値(5535756374)は DOG FACE 文字の UTF-16 の代理ペア表現です。これらの値は、U+D83D(十進値 55357)の上位代理価と、U+DC36 の下位代理値(十進値 56374)です。



Unicode のスカラー表現


その unicodeScalars プロパティを反復処理することによって String 値の Unicode スカラー表現にアクセスできます。このプロパティは UnicodeScalar 型の値の集合である UnicodeScalarView 型です。


UnicodeScalar には UInt32 の値内で表現されるスカラーの 21 ビット値を返す value プロパティがあります:


UnicodeScalar_2x


  1. for scalar in dogString.unicodeScalars {
  2.        print("\(scalar.value) ")
  3. }
  4. print("")
  5. // 68 111 103 8252 128054


最初の3つの UnicodeScalar 値(68、111、103)の value プロパティは再び文字 D、o、および g を表します。


4番目の codeUnit 値(8252)は再び 16 進値 203Cと等価な十進数であり、DOUBLE EXCLAMATION MARK 文字の Unicode スカラー U+203C を表します。


5番目と最後の UnicodeScalar,128054value プロパティは、16 進値 1F436 と 等価な十進数であり、DOG FACE 文字の Unicode スカラー U+1F436 を表します。


それらの value プロパティを照会する代わりに、各 UnicodeScalar 値はまた、文字列の補間のように、新しい String 値の構成のために使用できます。


  1. for scalar in dogString.unicodeScalars {
  2.        print("\(scalar) ")
  3. }
  4. // D
  5. // o
  6. // g
  7. // ‼
  8. // 🐶




前:基本演算子 次:コレクション型
目次
Xcode 10 の新機能

Swift:はじめに
Swift と Cocoa と Objective-C
Swift Blog より

  • ようこそ Swift へ(Part I)
  • Swift について
  • バージョン互換性
  • Swift のツアー
  • 単純な値
    制御フロー
    関数とクロージャ
    オブジェクトとクラス
    列挙型と構造体
    プロトコルと拡張機能
    エラー処理
    汎用(ジェネリック)
  • Swift 言語のガイド(Part II)
  • Swift の基本
  • 定数と変数
  • 定数と変数の宣言
    型注釈
    定数と変数の命名
    定数と変数の印刷
    コメント
    セミコロン
  • 整数
  • 整数の境界
    Int
    UInt
    浮動小数点数
    安全な型と型推論
    数値リテラル
  • 数値型変換
  • 整数変換
    整数と浮動小数点間の変換
    型エイリアス
    ブール型
    タプル
  • Optional
  • nil
    if 文と強制開封
    Optional の結合
    暗黙に開封された Optionals
    エラー処理
  • アサーション(断言)と前提条件
  • アサーションを使用したデバッグ
    前提条件の実施
  • 基本演算子
  • 専門用語
    代入演算子
  • 算術演算子
  • 剰余演算子
    単項マイナス演算子
    単項プラス演算子
    複合代入演算子
    比較演算子
    三項条件演算子
    Nil 合体演算子
  • 範囲演算子
  • 閉鎖範囲演算子
    半開放範囲演算子
    片方の範囲
  • 論理演算子
  • 論理 NOT 演算子
    論理 AND 演算子
    論理 OR 演算子
    論理演算子の組み合わせ
    明示的な括弧
  • 文字列と文字
  • 文字列リテラル
    複数行の文字列リテラル
    文字列リテラル内の特殊文字
    空の文字列の初期化
    文字列の可変性
    文字列は値の型
    文字を使った作業
    文字列と文字を連結
    文字列補間
  • ユニコード(Unicode)
  • Unicode スカラー
    文字列リテラルの中の特別の文字
    拡張書記クラスタ
    文字を数える
  • 文字列のアクセスと変更
  • 文字列のインデックス
    部分文字列
    挿入と削除
  • 文字列の比較
  • 文字列と文字の等価性
    接頭辞と接尾辞の等価性
  • 文字列の Unicode 表現
  • UTF-8 の表現
    UTF-16 表現
    Unicode のスカラー表現
  • コレクション型
  • コレクションの可変性
  • 配列
  • 配列型省略構文
    空の配列の作成
    デフォルト値を持つ配列の作成
    2つの配列を共にして一つの配列に
    配列リテラルでの配列の作成
    配列へのアクセスと変更
    配列の繰り返し処理
  • セット
  • セット型のハッシュ値
    セット型の構文
    空のセットの作成と初期化
    配列リテラルでセットの作成
    セットへのアクセスと変更
    セットを反復処理
  • セット操作の実行
  • 基本的なセットの操作
    セットの身分と等価性
  • Dictionary
  • Dictionary 型の省略型構文
    空の Dictionary を作成
    Dictionary リテラルで Dictionary の作成
    Dictionary のアクセスと変更
    Dictionary を繰り返し処理
  • フロー制御
  • For-In ループ
  • While ループ
  • While
    Repeat-While
  • 条件文
  • if 文
  • Switch
  • 暗黙の Fallthrough なし
    範囲の一致
    タプル(Tuples)
    値の結合
    Where
    複合した case
  • 制御転送文
  • Continue
  • Break
  • ループ文内の Break
    Switch 文内の Break
    Fallthrough
    ラベル付きの文
    早期終了
    API 利用可能性の確認
  • 関数
  • 関数の定義と呼び出し
  • 関数のパラメータと戻り値
  • パラメータなしの関数
    複数パラメータの関数
    戻り値なしの関数
    複数の戻り値を持つ関数
    optional のタプル型の戻り値
  • 関数引数のラベルとパラメータ名
  • 引数のラベルの指定
    引数ラベルの省略
    デフォルトのパラメータ値
    可変個引数のパラメータ
    In-Out パラメータ
  • 関数型
  • 関数型の使用
    パラメータ型としての関数型
    戻り値の型としての関数型
    入れ子になった関数
  • クロージャ
  • クロージャ式
  • ソートするメソッド
    クロージャ式の構文
    文脈から型を推論
    単一式クロージャからの暗黙的戻り値
    引数名の省略
    演算子メソッド
    後続クロージャ
    値のキャプチャ
    クロージャは参照型
    クロージャのエスケープ
    オートクロージャ
  • 列挙型
  • 列挙型の構文
    switch 文で列挙型の値の一致
    関連する値
  • 生の値
  • 暗黙に割り当てられた生の値
    生の値からの初期化
    再帰的な列挙型
  • クラスと構造体
  • クラスと構造体を比較
  • 定義の構文
    クラスと構造体のインスタンス
    プロパティにアクセス
    構造体型のためのメンバー化イニシャライザ
    構造体と列挙型は値型
  • クラスは参照型
  • ID 演算子
    ポインタ
    クラスと構造体の間の選択
    文字列、配列、辞書の代入とコピーの動作
  • プロパティ
  • 格納されたプロパティ
  • 定数構造体インスタンスの格納されたプロパティ
    遅延した格納されたプロパティ
    格納されたプロパティとインスタンス変数
  • 計算されたプロパティ
  • セッタ宣言の省略形
    読み取り専用の計算されたプロパティ
    プロパティ監視者
    グローバルとローカル変数
  • 型プロパティ
  • 型プロパティの構文
    型プロパティの照会と設定
  • メソッド
  • インスタンスメソッド
  • self プロパティ
    インスタンスメソッド内から値の型を変更
    変異メソッド内で self に代入
    型メソッド
  • サブスクリプト
  • サブスクリプトの構文
    サブスクリプトの使用法
    サブスクリプトのオプション
  • 継承
  • 基本クラスの定義
    サブクラス化
  • オーバーライド(上書き)
  • スーパークラスメソッド、プロパティ、サブスクリプトへのアクセス
    オーバーライドするメソッド
  • オーバーライドするプロパティ
  • プロパティのゲッタとセッタのオーバーライド
    プロパティ監視者のオーバーライド
    オーバーライドの防止
  • 初期化
  • 格納されたプロパティの初期値を設定
  • イニシャライザ
    デフォルトのプロパティ値
  • 初期化のカスタマイズ
  • 初期化パラメータ
    パラメータ名と引数ラベル
    引数ラベルのないイニシャライザのパラメータ
    Optional のプロパティ型
    初期化中に定数プロパティへの代入
  • デフォルトのイニシャライザ
  • 構造体型のためのメンバ化イニシャライザ
    値型のイニシャライザデリゲート
  • クラスの継承と初期化
  • 指定イニシャライザとコンビニエンスイニシャライザ
    指定とコンビニエンスイニシャライザの構文
    クラス型のイニシャライザデリゲート
    二相の初期化
    イニシャライザ継承とオーバーライド
    自動イニシャライザの継承
    実際の指定とコンビニエンスイニシャライザ
  • 失敗可能イニシャライザ
  • 生の値を持つ列挙型のための失敗可能イニシャライザ
    初期化失敗の伝播
    失敗可能イニシャライザのオーバーライド
    init! の失敗可能イニシャライザ
    必須イニシャライザ
    クロージャや関数でのデフォルトのプロパティ値設定
  • デイニシャライザ
  • デイニシャライザはどのように働くか
    作動中のデイニシャライザ
  • Optional の連鎖
  • 強制開封の代替としての Optional の連鎖
    Optional の連鎖のモデルクラスの定義
    Optional の連鎖を使用したプロパティへのアクセス
    Optional の連鎖を通じてメソッドを呼び出す
  • Optional の連鎖を通じてサブスクリプトへのアクセス
  • Optional 型のサブスクリプトにアクセス
    連鎖の複数レベルのリンク
    optional の戻り値を持つメソッドでの連鎖
  • エラー処理
  • エラーの表現と Throw
    エラーの処理
    throw 関数を使用したエラーの伝播
    Do-Catch を使用したエラー処理
    エラー をOptional の値に変換
    エラー伝播を無効に
    クリーンアップアクションの指定
  • 型キャスト
  • 型キャストのためのクラス階層の定義
    型のチェック
    ダウンキャスト
  • Any と AnyObjecgt 用の型キャスティング
  • ネストした型
  • 実際のネストした型
    ネストした型への参照
  • 拡張機能
  • 拡張機能の構文
    計算されたプロパティ
    イニシャライザ
  • メソッド
  • 変異インスタンスメソッド
    サブスクリプト
    ネストした型
  • プロトコル
  • プロトコルの構文
    プロパティの要件
    メソッドの要件
    変異メソッドの要件
  • イニシャライザの要件
  • プロトコルイニシャライザ要件のクラス実装
    失敗可能イニシャライザの要件
    型としてのプロトコル
    デリゲート
  • 拡張機能を持つプロトコル準拠の追加
  • 拡張機能を持つプロトコルの採用を宣言
    プロトコル型のコレクション
    プロトコルの継承
    クラス専用プロトコル
    プロトコルの構成
    プロトコル準拠の確認
    Optional のプロトコル要件
  • プロトコル拡張機能
  • デフォルトの実装の提供
    プロトコル拡張機能に制約を追加
  • ジェネリック(汎用)
  • 汎用が解決する問題
    汎用関数
    型パラメータ
    型パラメータの命名
    汎用の型
    汎用型の拡張
  • 型の制約
  • 型制約の構文
    実際の型の制約
  • 関連型
  • 実際の関連型
    既存の型を拡張して関連型を指定
    型注釈を使用して関連型を制約
    汎用の Where 句
    汎用の Where 句を含む拡張機能
    関連する型と汎用の Where 句
    汎用のサブスクリプト
  • 自動参照カウント
  • どのように ARC は働くか
    実際の ARC
    クラスインスタンス間の強い循環参照
  • クラスインスタンス間の強い循環参照の解決
  • 弱い参照
    所有されていない参照
    所有されていない参照と暗黙に開封された Optional のプロパティ
    クロージャの strong な循環参照
  • クロージャの strong な循環参照の解決
  • キャプチャリストの定義
    弱い参照と所有されていない参照
  • メモリの安全性
  • メモリへのアクセス競合の理解
    メモリアクセスの特徴
    In-Out パラメータへのアクセスの競合
    メソッド内の Self へのアクセスの競合
    プロパティへのアクセスの競合
  • アクセス制御
  • モジュールとソースファイル
  • アクセスレベル
  • アクセスレベルの全体的指針
    デフォルトのアクセスレベル
    ターゲット一つのアプリのアクセスレベル
    フレームワークのアクセスレベル
    ユニットテストのターゲット用のアクセスレベル
    アクセス制御の構文
  • カスタム型
  • タプル型
    関数型
  • 列挙型
  • 生の値と関連する値
    ネストした型
    サブクラス化
  • 定数、変数、プロパティ、およびサブスクリプト
  • ゲッタとセッタ
  • イニシャライザ
  • デフォルトのイニシャライザ
    構造体型用のデフォルトメンバ化イニシャライザ
  • プロトコル
  • プロトコルの継承
    プロトコルの準拠
  • 拡張機能
  • 拡張機能の private メンバ
    汎用
    型エイリアス
  • 高度な演算子
  • ビット単位演算子
  • ビット単位の NOT 演算子
    ビット単位の AND 演算子
    ビット単位の OR 演算子
    ビット単位の XOR 演算子
  • ビット単位の左と右シフト演算子
  • 符号なし整数のシフト動作
    符号付き整数のシフト動作
  • オーバーフロー演算子
  • 値オーバーフロー
    優先順位と結合性
  • 演算子メソッド
  • 接頭辞と接尾辞演算子
    複合代入演算子
    等価演算子
  • カスタム演算子
  • カスタム挿入辞演算子の優先順位
  • 言語のガイド(Part III)
  • 言語リファレンスについて
  • 文法の読み方
  • 語彙の構造
  • 空白とコメント
    識別子
    キーワードと句読点
  • リテラル
  • 整数リテラル
    浮動小数点リテラル
    文字列のリテラル
    演算子

  • 型注釈
    型識別子
    タプル型
    関数型
    エスケープしないクロージャの制限事項
    配列型
    辞書型
    Optional の型
    暗黙に開封された Optional の型
    プロトコル構成の型
    メタタイプ型
    型の継承句
    型の推測

  • 接頭辞式
    Try 演算子
  • 二項式
  • 代入演算子
    三項条件演算子
    型キャスト演算子
  • 一次式
  • リテラル式
    Self 式
    スーパークラス式
  • クロージャ式
  • キャプチャ・リスト
    暗黙のメンバ式
    括弧で囲まれた式
    タプル式
    ワイルドカード式
    キーパス式
    セレクタ式
    キーパス文字列式
  • 接尾辞の式
  • 関数呼び出し式
    イニシャライザ式
    明示的なメンバ式
    接尾辞の Self 式
    サブスクリプト 式
    強制値の式
    Optional の連鎖式

  • ループ文
  • For-In 文
    While 文
    Repeat-While 文
  • 分岐文
  • if 文
    Guard 文
  • switch 文
  • switch 文は、網羅的である必要あり
    実行が暗黙的に case を Fall Through しない
    ラベル付き文
  • 制御転送文
  • break 文
    continue 文
    fallthrough 文
    return 文
    throw 文
    defer 文
    do 文
  • コンパイラ制御文
  • 条件コンパイルブロック
    行制御文
    利用可能条件
  • 宣言
  • トップレベルのコード
    コードブロック
    Import 宣言
    ­定数の宣言
  • 変数の宣言
  • 格納された変数と格納された変数のプロパティ
    計算された変数と計算されたプロパティ
    格納された変数監視者とプロパティの監視者
    型変数プロパティ
    型エイリアス宣言
  • 関数の宣言
  • パラメータ名
    In-Out パラメータ
    パラメータの特殊な種類
    メソッドの特殊な種類
    Throw する関数とメソッド
    Rethrow する関数とメソッド
    決して返さない関数
  • 列挙型の宣言
  • 任意の型の case を列挙
  • 間接による列挙
    生の値型の case を列挙
    列挙型 case へのアクセス
    構造体の宣言
    クラスの宣言
  • プロトコルの宣言
  • プロトコル・プロパティ宣言
    プロトコル・メソッド宣言
    プロトコル・イニシャライザ宣言
    プロトコル・サブスクリプト宣言
    プロトコルに関連した型の宣言
  • イニシャライザ宣言
  • 失敗可能イニシャライザ
    デイニシャライザ宣言
    拡張機能の宣言
    サブスクリプト宣言
    演算子の宣言
    優先順位グループ宣言
  • 宣言修飾子
  • アクセス制御レベル
  • 属性
  • 宣言の属性
  • インターフェイスビルダーで使われる宣言属性
    型の属性
  • パターン
  • ワイルドカードパターン
    識別子パターン
    値結合パターン
    タプルパターン
    列挙型 case パターン
    Optional のパターン
    型キャストパターン
    式のパターン
  • 汎用パラメータと引数
  • 汎用パラメータ句
  • 汎用の where 句
    汎用引数句
  • 文法のまとめ
  • 語彙の構造



    宣言
    属性
    パターン
    汎用パラメータと引数
  • マニュアルの変更履歴
  • 変更履歴












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)












    トップへ(Swift Language Basics)