Parameter opsional default dalam fungsi Swift

107

Ketika saya mengatur firstThingke default nilini akan berfungsi, tanpa nilai default nilsaya mendapatkan kesalahan bahwa ada parameter yang hilang saat memanggil fungsi.

Dengan mengetik Int?saya pikir itu menjadikannya opsional dengan nilai default nil, apakah saya benar? Dan jika demikian, mengapa tidak berhasil tanpa = nil?

func test(firstThing: Int? = nil) {
    if firstThing != nil {
        print(firstThing!)
    }
    print("done")
}
test()
RickBrunstedt
sumber
1
Pertimbangkan bahwa Anda dapat menulis func test(firstThing: Int = 4): non- Optionalparameter dengan nilai default. The Optionaljenis (yang adalah apa ?dalam jenis nama mengembang ke) adalah jenis nilai; "parameter opsional" adalah nama yang tidak menguntungkan untuk parameter yang mungkin ada atau tidak ada pada panggilan fungsi, apa pun tipenya.
zneak
Versi Swift apa yang Anda gunakan untuk menguji kode ini? Kode Anda berfungsi dengan baik !! Opsional hanyalah sebuah tipe, dan parameter default berfungsi dengan baik seperti pada tipe lain di Swift
Victor Sigler

Jawaban:

210

Opsional dan parameter default adalah dua hal yang berbeda.

Opsional adalah variabel yang bisa nil, itu saja.

Parameter default menggunakan nilai default ketika Anda menghilangkan parameter itu, nilai default ini ditentukan seperti ini:func test(param: Int = 0)

Jika Anda menentukan parameter yang opsional, Anda harus menyediakannya, meskipun nilai yang ingin Anda teruskan adalah nil. Jika fungsi Anda terlihat seperti ini func test(param: Int?), Anda tidak dapat menyebutnya seperti ini test(). Meskipun parameternya opsional, ia tidak memiliki nilai default.

Anda juga dapat menggabungkan dua dan memiliki parameter yang mengambil opsional mana niladalah nilai default, seperti ini: func test(param: Int? = nil).

EmilioPelaez
sumber
27
"Jika Anda menentukan parameter yang opsional, Anda harus menyediakannya". Bagus, terima kasih Swift
andrewtweber
8
@andrewtweber Humor Anda dihargai, tetapi untuk pemula, saya pikir mungkin berguna untuk menjelaskan bahwa "Opsional" mengacu pada penyediaan objek atau nilai. Anda tidak perlu melakukan itu, Anda dapat memberikan nil (yang mewakili tidak adanya objek atau nilai). Anda hanya perlu memutuskan opsi mana yang Anda pilih.
JD Sandifer
23

Argumen default memungkinkan Anda memanggil fungsi tanpa memberikan argumen. Jika Anda tidak meneruskan argumen, maka argumen default akan disediakan. Jadi menggunakan kode Anda, ini ...

test()

... persis sama dengan ini:

test(nil)

Jika Anda membiarkan argumen default seperti ini ...

func test(firstThing: Int?) {
    if firstThing != nil {
        print(firstThing!)
    }
    print("done")
}

... maka Anda tidak dapat lagi melakukan ini ...

test()

Jika Anda melakukannya, Anda akan mendapatkan kesalahan "argumen yang hilang" yang Anda jelaskan. Anda harus menyampaikan argumen setiap saat, meskipun argumen itu hanya nil:

test(nil)   // this works
Aaron Rasmussen
sumber
18

Swift tidak seperti bahasa seperti JavaScript, di mana Anda dapat memanggil suatu fungsi tanpa melewatkan parameter dan itu akan tetap dipanggil. Jadi untuk memanggil fungsi di Swift, Anda perlu menetapkan nilai ke parameternya.

Nilai default untuk parameter memungkinkan Anda untuk menetapkan nilai tanpa menentukannya saat memanggil fungsi. Itulah mengapa test()berfungsi ketika Anda menentukan nilai default pada deklarasi test.

Jika Anda tidak menyertakan bahwa nilai default, Anda perlu memberikan nilai pada panggilan: test(nil).

Selain itu, dan tidak terkait langsung dengan pertanyaan ini, tetapi mungkin perlu diperhatikan, Anda menggunakan cara "C ++" untuk menangani kemungkinan pointer nol, untuk menangani kemungkinan opsional nil di Swift. Kode berikut lebih aman (khususnya dalam perangkat lunak multithreading), dan memungkinkan Anda menghindari pembongkaran paksa opsional:

func test(firstThing: Int? = nil) {
    if let firstThing = firstThing {
        print(firstThing)
    }
    print("done")
}
test()
nbloqs
sumber
7

Anda menggabungkan Optionaldengan memiliki default. An Optionalmenerima nilai atau nihil. Memiliki default memungkinkan argumen dihilangkan dalam memanggil fungsi. Argumen dapat memiliki nilai default dengan atau tanpa Optionaltipe.

func someFunc(param1: String?,
          param2: String = "default value",
          param3: String? = "also has default value") {
    print("param1 = \(param1)")

    print("param2 = \(param2)")

    print("param3 = \(param3)")
}

Contoh panggilan dengan keluaran:

someFunc(param1: nil, param2: "specific value", param3: "also specific value")

param1 = nil
param2 = specific value
param3 = Optional("also specific value")

someFunc(param1: "has a value")

param1 = Optional("has a value")
param2 = default value
param3 = Optional("also has default value")

someFunc(param1: nil, param3: nil)

param1 = nil
param2 = default value
param3 = nil

Untuk meringkas:

  • Ketik dengan? (misalnya String?) adalah Optionalmungkin nil atau mungkin berisi turunan dari Type
  • Argumen dengan nilai default dapat dihilangkan dari panggilan ke fungsi dan nilai default akan digunakan
  • Jika keduanya Optionaldan memiliki default, maka itu dapat dihilangkan dari pemanggilan fungsi ATAU dapat dimasukkan dan dapat diberikan dengan nilai nil (misalnya param1: nil)
Chuck Krutsinger
sumber
dapatkah saya menambahkan parameter default sebagai variabel seperti let atau var? Terima kasih
Yogesh Patel
@YogeshPatel Tidak yakin apa yang Anda maksud.
Chuck Krutsinger
seperti var myName = "Yogesh". Sekarang, fungsi saya seperti 1. func getFilterNames (name: string = myName) {} pendekatan ini tidak bekerja untuk saya. 2. func getFilterNames (name: string = "Yogesh") {} pendekatan ini berhasil untuk saya. Tetapi saya ingin yang pertama jadi bisakah Anda membantu saya untuk mencapai ini. Terima kasih banyak!
Yogesh Patel
@YogeshPatel Saya pikir apa yang Anda inginkan adalah func getFilterNames(name: inout String){ }yang memungkinkan Anda mengubah nama yang diberikan.
Chuck Krutsinger
Tidak, tidak, Pak. saya tidak ingin mengubah parameter saya. saya hanya ingin memberikan nilai default untuk parameter saya tetapi tidak seperti statis "Yogesh". saya ingin melakukan seperti biarkan name = "Yogesh" dynamic func getFilterNames (name: string = name) seperti ini. mendapatkan ini Pak? Terima kasih!
Yogesh Patel
4

jika Anda perlu menggunakan parameter bool, Anda hanya perlu menetapkan nilai default.

func test(WithFlag flag: Bool = false){.....}

maka Anda dapat menggunakan tanpa atau dengan param:

test() //here flag automatically has the default value: false
test(WithFlag: true) //here flag has the value: true
Niib Fouda
sumber
Untuk orang yang tidak menyukai ini, Anda dapat memperbaiki hal yang salah, sehingga orang lain akan mengerti.
Niib Fouda
3

"Parameter opsional" berarti "jenis parameter ini opsional". Ini tidak berarti "Parameter ini opsional dan, oleh karena itu, dapat diabaikan saat Anda memanggil fungsi".

Istilah "parameter opsional" tampaknya membingungkan. Untuk memperjelas, lebih akurat mengatakan "parameter jenis opsional" daripada "parameter opsional" karena kata "opsional" di sini hanya dimaksudkan untuk menjelaskan jenis nilai parameter dan tidak ada yang lain.

Todanley
sumber
0

Jika Anda ingin dapat memanggil funcdengan atau tanpa parameter, Anda dapat membuat yang kedua funcdari nama yang sama yang memanggil yang lain.

func test(firstThing: Int?) {
    if firstThing != nil {
        print(firstThing!)
    }
    print("done")
}

func test() {
    test(firstThing: nil)
}

sekarang Anda dapat memanggil fungsi bernama testtanpa atau tanpa parameter.

// both work
test()
test(firstThing: 5)
Sean256
sumber
Mengapa Anda mendefinisikan fungsi tambahan ketika Anda bisa menentukan nil sebagai nilai default untuk parameter?
Peter Schorn
-1

Ini sedikit rumit ketika Anda mencoba menggabungkan parameter opsional dan nilai default untuk parameter itu. Seperti ini,

func test(param: Int? = nil)

Keduanya adalah ide yang sangat berlawanan. Jika Anda memiliki parameter tipe opsional tetapi Anda juga memberikan nilai default padanya, sekarang ini bukan lagi tipe opsional karena memiliki nilai default. Meskipun defaultnya nihil, swift hanya menghapus pengikatan opsional tanpa memeriksa nilai defaultnya.

Jadi selalu lebih baik untuk tidak menggunakan nil sebagai nilai default.

Shubham Naik
sumber
1
Ini salah Tidak ada yang salah dengan opsional yang memiliki nilai default (genap nil).
Brian Kendig
apa yang saya katakan adalah sekali variabel memiliki nilai default, itu bukan opsional dalam arti akan selalu memiliki nilai.
Shubham Naik
1
Itu tidak benar, dan saya tidak yakin apa yang Anda coba gambarkan. Saya pikir Anda benar mengatakan bahwa sekali variabel memiliki nilai yang diberikan padanya, itu akan selalu diberikan; Anda tidak dapat membatalkan penetapannya (juga tidak ingin melakukannya) kecuali Anda membatalkan alokasinya. Dan Swift akan memberi Anda kesalahan kompilasi jika Anda mencoba menggunakan variabel sebelum memiliki nilai (seperti dalam var foo: String; print(foo)). Tapi argumen fungsi dengan nilai default adalah argumen opsional (Anda tidak harus meneruskannya dalam pemanggilan fungsi) dan bisa juga dalam tipe Opsional (memungkinkan niluntuk ditetapkan padanya, bahkan sebagai nilai default).
Brian Kendig
Opsional pada dasarnya adalah tipe gabungan dari <Type | Nil>, yaitu dapat memiliki tipe Tertentu atau Tipe Nihil. (Dengan asumsi swift memiliki Serikat, yang sebenarnya tidak, tapi kita berbicara secara konseptual di sini). jadi Int? = nol baik-baik saja.
Shayne
-1

Nilai default tidak berarti nilai default dari tipe data. Di sini nilai default berarti nilai yang ditentukan pada saat mendefinisikan fungsi. kita harus mendeklarasikan nilai default variabel saat mendefinisikan variabel dalam fungsi.

Mahesh Kulkarni
sumber