Operator relasional adalah alat utama kita untuk membuat keputusan berdasarkan kondisi data. Tanpa operator relasional, sebuah program C tidak akan bisa memutuskan apakah seorang pengguna berhak masuk, apakah suhu ruangan masih aman, atau apakah stok barang menipis. Pada Chapter ini kita akan menelaah enam operator relasional di C, perilaku khusus yang menghasilkan nilai int 0 atau 1 (bukan tipe bool), serta jebakan klasik berupa perbandingan bilangan floating-point yang sering menghasilkan hasil mengejutkan karena masalah presisi.

Enam Operator Relasional #

C memiliki enam operator relasional yang membandingkan dua nilai dan menghasilkan nilai bertipe int bernilai 0 (salah) atau 1 (benar). Pemilihan int sebagai tipe hasil berakar pada sejarah C yang lahir sebelum tipe _Bool diperkenalkan di C99.

OperatorArtiContoh a=10, b=20Hasil
==Sama dengan10 == 200
!=Tidak sama dengan10 != 201
<Lebih kecil10 < 201
<=Lebih kecil atau sama10 <= 201
>Lebih besar10 > 200
>=Lebih besar atau sama10 >= 200
c
#include <stdio.h>

int main(void) {
    int a = 10;
    int b = 20;

    printf("a == b : %d\n", a == b);
    printf("a != b : %d\n", a != b);
    printf("a <  b : %d\n", a <  b);
    printf("a <= b : %d\n", a <= b);
    printf("a >  b : %d\n", a >  b);
    printf("a >= b : %d\n", a >= b);
    return 0;
}

Output yang Dihasilkan:

text
a == b : 0
a != b : 1
a <  b : 1
a <= b : 1
a >  b : 0
a >= b : 0

Mari kita telaah baris-baris kode di atas:

  1. Baris 7 (printf("a == b : %d\n", a == b);): ekspresi a == b dievaluasi menjadi 0 karena 10 tidak sama dengan 20; nilai 0 ini dicetak dengan format specifier %d.
  2. Baris 8 (printf("a != b : %d\n", a != b);): ekspresi a != b menghasilkan 1 (benar) karena 10 memang berbeda dengan 20.
  3. Baris 9-12: setiap operator relasional menghasilkan int 0 atau 1 sesuai tabel di atas; tidak ada nilai perantara seperti 0.5 atau "true".

Hasil Relasional Adalah Nilai int #

Berbeda dengan banyak bahasa modern yang memakai tipe boolean khusus, C mengembalikan hasil operator relasional sebagai int bernilai 0 atau 1. Konsekuensinya, hasil perbandingan bisa langsung kita simpan ke variabel int, kita jumlahkan untuk menghitung berapa kondisi yang terpenuhi, atau kita pakai sebagai kondisi pada if, while, dan for.

c
#include <stdio.h>

int main(void) {
    int suhu = 38;
    int batas_demam = 37;

    /* Simpan hasil perbandingan ke variabel int */
    int demam = (suhu > batas_demam);

    printf("Suhu           : %d C\n", suhu);
    printf("Batas demam    : %d C\n", batas_demam);
    printf("Apakah demam?  : %d\n", demam);

    if (demam) {
        printf("Keputusan      : perlu istirahat\n");
    } else {
        printf("Keputusan      : sehat\n");
    }
    return 0;
}

Output yang Dihasilkan:

text
Suhu           : 38 C
Batas demam    : 37 C
Apakah demam?  : 1
Keputusan      : perlu istirahat

Pada baris ke-8, ekspresi suhu > batas_demam menghasilkan 1 dan disalin ke variabel demam. Karena dalam C setiap nilai non-zero dianggap benar, pernyataan if (demam) memilih cabang “perlu istirahat” tanpa perbandingan eksplisit seperti if (demam == 1).

Jebakan: Membandingkan Bilangan Floating-Point #

Operator == pada bilangan floating-point sering kali tidak menghasilkan 1 meskipun secara matematis kedua nilai seharusnya sama. Hal ini terjadi karena bilangan floating-point disimpan dalam representasi biner yang tidak dapat merepresentasikan pecahan desimal seperti 0.1 atau 0.3 secara eksak. Akibatnya, hasil penjumlahan 0.1 + 0.2 tidak persis sama dengan 0.3, melainkan sedikit lebih besar atau lebih kecil.

c
#include <stdio.h>

int main(void) {
    /* Jebakan: membandingkan float dengan == */
    double harga = 0.1 + 0.2;
    double target = 0.3;

    printf("harga  = %.17f\n", harga);
    printf("target = %.17f\n", target);
    printf("harga == target ? %d\n", harga == target);
    printf("harga <  target  ? %d\n", harga < target);
    return 0;
}

Output yang Dihasilkan:

text
harga  = 0.30000000000000004
target = 0.29999999999999999
harga == target ? 0
harga <  target  ? 0

Walaupun secara matematis 0.1 + 0.2 sama dengan 0.3, perbandingan harga == target menghasilkan 0 (salah) karena harga sebenarnya bernilai 0.30000000000000004, sedangkan target bernilai 0.29999999999999999. Operator < pun menghasilkan 0 karena selisihnya sangat kecil namun tetap positif.

Subjek Pembanding Harus Sejenis #

Operator relasional mengharapkan kedua operand memiliki tipe yang sebanding. Jika tipe berbeda (misalnya int dan double), compiler akan menerapkan usual arithmetic conversions untuk menyamakan keduanya sebelum perbandingan dilakukan—topik yang akan kita dalami pada Chapter khusus. Untuk membandingkan dua string, kita tidak bisa memakai == karena yang dibandingkan adalah alamat pointer, bukan isi karakter. Operasi perbandingan string harus memakai fungsi strcmp() dari <string.h>.

Dengan pemahaman ini, kita siap melangkah ke operator logika yang memungkinkan kita menggabungkan beberapa kondisi relasional menjadi satu keputusan yang lebih kompleks.