Deklarasi, konstanta, dan pola var

Tip

Artikel ini adalah bagian dari bagian Dasar-Dasar untuk pengembang yang sudah mengetahui setidaknya satu bahasa pemrograman dan mempelajari C#. Mulailah dengan gambaran umum pencocokan pola jika Anda belum menggunakan pola C# sebelumnya. Untuk aturan bahasa lengkap, lihat referensi pola.

Pola diterapkan pada ekspresi masukan. C# mengevaluasi ekspresi, lalu pola menguji atau menangkap nilai yang dihasilkan. Deklarasi, konstanta, dan var pola menjawab tiga pertanyaan praktis:

  • Pola deklarasi: Apakah ekspresi menghasilkan nilai non-null dari jenis run-time yang kompatibel? Jika demikian, deklarasikan variabel untuk nilai tersebut.
  • Pola konstanta: Apakah ekspresi menghasilkan satu nilai konstanta tertentu?
  • var pola: Nilai apa yang dihasilkan ekspresi? Tangkap tanpa terlebih dahulu menguji jenis atau nilainya.

Menguji dan menangkap tipe dengan pola deklarasi

Pola deklarasi terdiri dari jenis dan penunjukan. Jenis menentukan jenis run-time apa yang akan diuji. Penunjukan mendeklarasikan variabel yang menerima nilai yang cocok.

Contoh berikut menerima object, sehingga ekspresi mungkin menghasilkan banyak jenis yang berbeda. Pola deklarasi memungkinkan cabang yang cocok menggunakan nilai desimal tanpa pengujian tipe dan konversi tipe secara terpisah:

static void PrintPrice(object value)
{
    if (value is decimal amount)
    {
        Console.WriteLine($"Price: {amount:C}");
    }
}

Dalam value is decimal amount:

  • value adalah ekspresi input. C# mengevaluasinya terlebih dahulu.
  • decimal adalah jenis yang diuji. Pola cocok ketika nilai yang dievaluasi non-null dan jenis run-time-nya kompatibel dengan decimal.
  • amount adalah sebutannya. Ketika pola cocok, amount dideklarasikan dan diberi nilai desimal.

Pengkompilasi melacak apakah variabel lokal menerima nilai sebelum kode Anda membacanya. Pelacakan ini disebut penetapan yang pasti. Di dalam blok if, pengkompilasi mengetahui bahwa amount telah diberi nilai karena blok tersebut hanya dijalankan ketika pola cocok. Pengkompilasi menghasilkan kesalahan jika kode Anda mencoba mengakses amount di luar if blok. Jika value bukan decimal nilai, variabel amount tidak ditetapkan ke nilai.

Pilih pola deklarasi saat cabang yang cocok perlu menggunakan hasilnya sebagai jenis yang diuji. Ini menggabungkan tes, konversi, dan deklarasi variabel, sehingga tidak perlu mengulang ekspresi atau menulis cast terpisah.

Anda juga dapat menggunakan pola deklarasi saat satu ekspresi mungkin menghasilkan beberapa jenis yang berguna:

static string FormatSensorValue(object reading) =>
    reading switch
    {
        int count => $"Count: {count}",
        double temperature => $"Temperature: {temperature:F1}°C",
        string message => $"Message: {message}",
        _ => "Unsupported reading"
    };

Setiap lengan mendeklarasikan variabel dari jenis yang cocok karena hasilnya membutuhkan perilaku pemformatan jenis tersebut. Pola deklarasi hanya akan sesuai ketika nilai yang dievaluasi tidak null dan sudah memiliki tipe run-time yang kompatibel dengan tipe yang diuji melalui konversi yang diizinkan dalam pola. null tidak memiliki jenis run-time untuk mencocokkan pola. Pola ini juga tidak menjalankan operator konversi yang ditentukan pengguna: Ini adalah pengujian dan pengambilan jenis, bukan permintaan untuk mengonversi nilai ke jenis lain. Untuk aturan kompatibilitas lengkap, lihat Deklarasi dan pola jenis.

Mencocokkan nilai tertentu dengan pola konstanta

Pola konstan menguji apakah ekspresi menghasilkan konstanta tertentu, seperti angka, string, Boolean, anggota enum, nilai yang dideklarasikanconst, atau null.

Pola konstanta pas dengan ekspresi pengalihan saat beberapa nilai yang diketahui masing-masing menghasilkan hasil yang berbeda:

static string GetCommandMessage(Command command) =>
    command switch
    {
        Command.Start => "Starting",
        Command.Stop => "Stopping",
        Command.Pause => "Pausing",
        _ => "Unknown command"
    };

Command adalah enum, jenis yang mendefinisikan sekumpulan konstanta bernama. Command.Start, Command.Stop, dan Command.Pause merupakan anggota enumnya, sehingga setiap lengan sakelar menggunakan pola konstan untuk menguji satu nilai perintah bernama.

Pilih formulir ini ketika perintah dapat memiliki beberapa arti diskrit. Lengan sakelar menyimpan nilai dan hasilnya bersama-sama. Untuk satu perbandingan kesetaraan sederhana, if pernyataan seperti if (command == Command.Start) biasanya lebih mudah dibaca.

Pencocokan pola konstan menggunakan aturan kesetaraan bawaan bahasa, bukan operator == yang ditentukan pengguna. Untuk aturan kesetaraan dan konversi terperinci, lihat referensi pola konstan.

Pola null konstanta berguna untuk pemeriksaan null yang andal:

static bool HasText(string? text) => text is not null;

Pilih is null atau is not null saat Anda memeriksa status null. Pola-pola ini tidak memanggil operator kesetaraan yang ditentukan pengguna, bahkan ketika jenis ekspresi kelebihan beban ==.

Mengambil hasil untuk penjaga dengan var pola

Polavar cocok dengan setiap hasil, termasuk null, dan mendeklarasikan variabel yang jenisnya adalah jenis waktu kompilasi ekspresi input. Ini dapat menangkap nilai komputasi sementara pola lain sudah cocok dengan objek:

static string GetDeliveryMessage(object delivery) =>
    delivery switch
    {
        ExpressDelivery express
            when EstimateDays(express) is var days && days <= 2
                => $"Arrives in {days} day{(days == 1 ? "" : "s")}",
        ExpressDelivery => "Express delivery for your location takes more than two days",
        _ => "Standard delivery"
    };

static int EstimateDays(ExpressDelivery delivery) =>
    delivery.MilesAway <= 500 ? 1 :
    delivery.MilesAway <= 1_000 ? 2 : 3;

record ExpressDelivery(int MilesAway);

Pola deklarasi ExpressDelivery express pertama kali menangkap objek pengiriman sebagai express. Pemanggilan metode EstimateDays(express) adalah ekspresi masukan untuk pola var. C# mengevaluasi pemanggilan metode tersebut, dan var days menyimpan perkiraan yang dihasilkan sebagai days tanpa menguji jenis atau nilainya. Perkiraannya bisa satu atau dua hari ketika penjaga berhasil. Hasil lengan membutuhkan nilai yang diambil untuk melaporkan jumlah hari yang sebenarnya.

Variabel lokal biasa tidak dapat dideklarasikan di antara pola switch-arm dan guard when-nya. Memanggil EstimateDays(express) lagi dalam hasil akan mengulangi perhitungan. Pilih bentuk pola var ini ketika kode sudah sesuai, dan guard serta hasil memerlukan nilai antara yang dihitung.

Jika Anda tidak memerlukan nilai yang diambil, gunakan pola _buang alih-alih mendeklarasikan variabel.

Baca juga