Swift - Chia chuỗi trên nhiều dòng


265

Làm thế nào tôi có thể chia một chuỗi trên nhiều dòng như dưới đây?

var text:String = "This is some text
                   over multiple lines"

Để tự động chuyển đổi các dòng thành một chuỗi nhiều dòng, hãy xem câu trả lời của tôi về chủ đề hơi liên quan này. Làm thế nào bạn có thể triển khai macro chuỗi chữ đa dòng này trong Swift?
holroy

Câu trả lời:


444

Swift 4 bao gồm hỗ trợ cho chuỗi ký tự nhiều dòng . Ngoài các dòng mới, họ cũng có thể chứa các trích dẫn không được giải thích.

var text = """
    This is some text
    over multiple lines
    """

Các phiên bản cũ hơn của Swift không cho phép bạn có một chữ duy nhất trên nhiều dòng nhưng bạn có thể thêm các chữ cùng nhau trên nhiều dòng:

var text = "This is some text\n"
         + "over multiple lines\n"

2
Vấn đề với cách tiếp cận đó là bạn có thể dễ dàng tiếp cận quá nhiều dòng 'tiếp tục' trong Swift (kể từ Xcode 6.2 beta), trong đó nó phàn nàn biểu thức là "quá phức tạp để giải quyết trong một khoảng thời gian hợp lý" và xem xét việc phá vỡ nó xuống biểu thức đơn giản hơn. Điều đó xấu xí nhưng đủ dễ để thực hiện, chỉ cần bọc các phần trong parens.
chiếu sáng

8
Đừng quên thêm khoảng trắng giữa dấu ngoặc kép và dấu +, nếu không, bạn sẽ gặp lỗi "'+' không phải là một toán tử đơn vị hậu tố"
Orlin Georgiev

Điều này vẫn hoạt động, nhưng bạn cần thêm thủ công \nnhân vật. Ví dụ: trong REPL: println("foo\n" + "bar")in foobartrên các dòng riêng biệt.
Brian Gerstle

Nó cần được cố định trong Xcode 7 "Concatenation của Swift xâu, kể cả trên nhiều dòng, là một tối ưu hóa thời gian biên dịch đảm bảo, ngay cả ở -Onone,." Adcdownload.apple.com/WWDC_2015/Xcode_7_beta/...
Kostiantyn Koval

2
Không hoạt động cho các giá trị trường hợp enum sử dụng chuỗi :(
Lars Blumberg

32

Tôi đã sử dụng một phần mở rộng trên String để đạt được các chuỗi multiline trong khi tránh lỗi treo trình biên dịch. Nó cũng cho phép bạn chỉ định một dấu phân cách để bạn có thể sử dụng nó giống như hàm tham gia của Python

extension String {
    init(sep:String, _ lines:String...){
        self = ""
        for (idx, item) in lines.enumerated() {
            self += "\(item)"
            if idx < lines.count-1 {
                self += sep
            }
        }
    }

    init(_ lines:String...){
        self = ""
        for (idx, item) in lines.enumerated() {
            self += "\(item)"
            if idx < lines.count-1 {
                self += "\n"
            }
        }
    }
}



print(
    String(
        "Hello",
        "World!"
    )
)
"Hello
World!"

print(
    String(sep:", ",
        "Hello",
        "World!"
    )
)
"Hello, World!"

1
Những phương pháp này là hoàn hảo. Ngay cả trong phiên bản 1.2 Swift mới nhất, các chữ dài được biên dịch rất chậm và các phương thức này tránh được chi phí đó.
phatmann 19/03/2015

2
Đối với bất cứ ai sử dụng Swift 2, enumerate(lines)giờ đâylines.enumerate()
Jedidja

2
@mcornell Điều này là tốt, nhưng joinWithSeparatorvề cơ bản không làm điều tương tự? ["Hello", "World!"].joinWithSeparator(", ")
Dan Loewenherz

27

Đây là điều đáng thất vọng đầu tiên về Swift mà tôi nhận thấy. Hầu như tất cả các ngôn ngữ kịch bản cho phép các chuỗi nhiều dòng.

C ++ 11 đã thêm chuỗi ký tự thô cho phép bạn xác định dấu kết thúc của riêng mình

C # có @literals cho chuỗi nhiều dòng.

Ngay cả C đơn giản và do đó, C ++ và Objective-C lỗi thời cho phép kết nối đơn giản bằng cách đặt nhiều chữ bên cạnh, do đó các trích dẫn được thu gọn. Khoảng trắng không được tính khi bạn làm điều đó để bạn có thể đặt chúng trên các dòng khác nhau (nhưng cần thêm dòng mới của riêng bạn):

const char* text = "This is some text\n"
                   "over multiple lines";

Vì swift không biết rằng bạn đã đặt văn bản của mình trên nhiều dòng, tôi phải sửa mẫu của con trỏ, tương tự như mẫu C của tôi, nêu rõ dòng mới:

var text:String = "This is some text \n" +
                  "over multiple lines"

4
Tôi khá chắc chắn rằng có những hạn chế trong việc này. Tôi đã thử chia một chuỗi trên 13 dòng (Đó là văn bản thông tin nhiều dòng). Nó không chỉ không hoàn thành việc biên dịch mà còn khiến máy Mac của tôi quỳ xuống. Như tôi nói, tôi không thể nói một cách cụ thể đây là một vấn đề, nhưng hãy cẩn thận, tác động khá tệ.
Hiệp sĩ Derek

Tôi đã bị rơi nhiều lần ngay cả trước khi biên dịch. Tôi nghĩ rằng quy trình "SourceKitService" chịu trách nhiệm về tô sáng cú pháp và hoàn thành mã (tôi cho rằng) cũng chịu trách nhiệm cho sự cố này.
Paul Brewczynski

@DerekKnight Đó là lỗi trình biên dịch, không giới hạn ngôn ngữ. Nếu nó vẫn còn, bạn nên nộp một Radar.
radex

@bluesm FYI: SourceKit là một quy trình riêng biệt, vì vậy nó không thể sập Xcode. Nó thực hiện tô sáng cú pháp và hoàn tất mã, chính xác, nhưng hiện tại, bản biên dịch tồn tại trong quy trình của Xcode - đó là lý do tại sao một lỗi trình biên dịch làm mất Xcode đôi khi :(
radex

17

Chuỗi nhiều dòng có thể có trong Swift 4.0, nhưng có một số quy tắc:

  1. Bạn cần bắt đầu và kết thúc chuỗi của mình bằng ba dấu ngoặc kép , """.
  2. Nội dung chuỗi của bạn nên bắt đầu trên dòng riêng của nó.
  3. Việc chấm dứt """cũng nên bắt đầu trên dòng riêng của nó.

Ngoài ra, bạn tốt để đi! Đây là một ví dụ:

let longString = """
When you write a string that spans multiple
lines make sure you start its content on a
line all of its own, and end it with three
quotes also on a line of their own.
Multi-line strings also let you write "quote marks"
freely inside your strings, which is great!
"""

Xem những gì mới trong Swift 4 để biết thêm thông tin.


Thật không may, điều này không hoạt động trong Sân chơi Xcode 8.3.3. Tôi nhận được một lỗi "chuỗi unterminated".
James Foster

Như tôi đã nói, tính năng này là mới trong Swift 4 - cài đặt chuỗi công cụ Swift 4 vào Xcode 8.3.3 hoặc cài đặt Xcode 9.
TwoStraws

16

Như được chỉ ra bởi litso, việc sử dụng lặp lại +-Operator trong một biểu thức có thể dẫn đến treo XCode Beta (chỉ được kiểm tra với XCode 6 Beta 5): Xcode 6 Beta không biên dịch

Một thay thế cho các chuỗi nhiều dòng bây giờ là sử dụng một chuỗi các chuỗi và reducenó với +:

var text = ["This is some text ",
            "over multiple lines"].reduce("", +)

Hoặc, đơn giản hơn, sử dụng join:

var text = "".join(["This is some text ",
                    "over multiple lines"])

Phiên bản rút gọn hoạt động với tôi trên phiên bản beta 6, nhưng việc tham gia đã tạo ra một ngoại lệ.
Tristan Warner-Smith

9

Swift 4 đã giải quyết vấn đề này bằng cách hỗ trợ chuỗi ký tự nhiều dòng như bạn sẽ viết trong notepad hoặc bất kỳ trình soạn thảo văn bản nào. Để kết thúc chuỗi nhiều dòng chữ một lần nữa, hãy viết lại

Xem ví dụ dưới đây

     let multiLineStringLiteral = """
    This is one of the best feature add in Swift 4
    It let’s you write “Double Quotes” without any escaping
    and new lines without need of “\n”
    """

print(multiLineStringLiteral)

5

Nhanh:

@connor là câu trả lời đúng, nhưng nếu bạn muốn thêm các dòng trong câu lệnh in mà bạn đang tìm kiếm \nvà / hoặc \r, chúng được gọi là Escape Sequences hoặc Escged character , đây là liên kết đến tài liệu của Apple về chủ đề này. .

Thí dụ:

print("First line\nSecond Line\rThirdLine...")

6
Đây không phải là bất cứ ai muốn. Chúng tôi muốn có thể có các kết thúc dòng trong mã nguồn cho chuỗi ký tự, không (nhất thiết) có ngắt dòng trong đầu ra được kết xuất . Điều này khá rõ ràng trong câu hỏi ban đầu, tôi nghĩ vậy. Những người có điểm số tích cực rõ ràng hiểu. Những người có điểm số rõ ràng là không.
ArtOfWarfare

5
@ArtOfWarfare đây là câu trả lời tôi đang tìm kiếm và trang này là kết quả hàng đầu khi thực hiện tìm kiếm "chuỗi swift dòng mới". Rõ ràng, nó không rõ ràng như bạn nói.
John R Perry

4

Thêm vào câu trả lời @Connor, cũng cần phải có \ n. Đây là mã sửa đổi:

var text:String = "This is some text \n" +
                  "over multiple lines"

3

Ví dụ sau mô tả việc tiếp tục nhiều dòng, sử dụng dấu ngoặc đơn như một cách giải quyết đơn giản cho lỗi Swift kể từ Xcode 6.2 Beta, trong đó nó phàn nàn biểu thức quá phức tạp để giải quyết trong một khoảng thời gian hợp lý và xem xét chia nhỏ nó thành nhỏ hơn miếng:

    .
    .
    .
    return String(format:"\n" +
                    ("    part1:    %d\n"    +
                     "    part2:    %d\n"    +
                     "    part3:  \"%@\"\n"  +
                     "    part4:  \"%@\"\n"  +
                     "    part5:  \"%@\"\n"  +
                     "    part6:  \"%@\"\n") +
                    ("    part7:  \"%@\"\n"  +
                     "    part8:  \"%@\"\n"  +
                     "    part9:  \"%@\"\n"  +
                     "    part10: \"%@\"\n"  +
                     "    part12: \"%@\"\n") +
                     "    part13:  %f\n"     +
                     "    part14:  %f\n\n",
                    part1, part2, part3, part4, part5, part6, part7, part8, 
                    part9, part10, part11, part12, part13, part14)
    .
    .
    .

0

Một cách khác nếu bạn muốn sử dụng biến chuỗi với một số văn bản được xác định trước,

var textFieldData:String = "John"
myTextField.text = NSString(format: "Hello User, \n %@",textFieldData) as String
myTextField.numberOfLines = 0

0

Bạn có thể sử dụng unicode bằng để nhập hoặc \nthực hiện chúng bên trong chuỗi của bạn. Ví dụ : \u{0085}.


0

Mẫu vật

var yourString = "first line \n second line \n third line"

Trong trường hợp, bạn không tìm thấy toán tử + phù hợp


0

Một cách tiếp cận là đặt văn bản nhãn thành AttText và cập nhật biến chuỗi để bao gồm HTML cho ngắt dòng ( <br />).

Ví dụ:

var text:String = "This is some text<br />over multiple lines"
label.attributedText = text

Đầu ra:

This is some text
over multiple lines

Hi vọng điêu nay co ich!


Bạn không thể gán Stringgiá trị (văn bản) cho thuộc NSAttributedString?tính (nhãn.attributionText).
Maxime Ashurov

0

Đây là đoạn mã để phân tách một chuỗi bởi n ký tự được phân tách trên các dòng:

//: A UIKit based Playground for presenting user interface

import UIKit
import PlaygroundSupport

class MyViewController : UIViewController {
    override func loadView() {

        let str = String(charsPerLine: 5, "Hello World!")
        print(str) // "Hello\n Worl\nd!\n"

    }
}

extension String {

    init(charsPerLine:Int, _ str:String){

        self = ""
        var idx = 0
        for char in str {
            self += "\(char)"
            idx = idx + 1
            if idx == charsPerLine {
                self += "\n"
                idx = 0
            }
        }

    }
}

-3

Tôi đã thử một vài cách nhưng tìm thấy một giải pháp thậm chí tốt hơn: Chỉ cần sử dụng yếu tố "Chế độ xem văn bản". Đó là văn bản hiển thị nhiều dòng tự động! Tìm thấy ở đây: UITextField nhiều dòng


(chỉ để bạn biết, downvotes có lẽ vì câu hỏi là về định dạng trong mã, không phải trong giao diện người dùng ... và cung cấp một mẫu mã trong câu trả lời của bạn có lẽ đã thực hiện này rõ ràng hơn)
ghế tập cơ bắp
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.