Menu
CoddyTech

Pola Strategy

Termasuk bagian Pemrograman Berorientasi Object dalam perjalanan C++ di Coddy. Pelajaran 95 dari 104.

Pola Strategy mendefinisikan keluarga algoritma, mengenkapsulasi setiap algoritma, dan membuatnya dapat saling dipertukarkan. Ini memungkinkan kamu mengubah perilaku object saat program berjalan tanpa mengubah kodemu. Algoritma tersebut bervariasi secara independen dari client yang menggunakannya.

Pola ini terdiri dari tiga bagian: interface Strategy yang mendeklarasikan method algoritma, Strategi Konkret yang menerapkan variasi berbeda, dan Konteks yang menggunakan sebuah strategi:

#include <iostream>
#include <memory>

// Antarmuka strategi
class PaymentStrategy {
public:
    virtual void pay(int amount) = 0;
    virtual ~PaymentStrategy() = default;
};

// Strategi konkret
class CreditCardPayment : public PaymentStrategy {
public:
    void pay(int amount) override {
        std::cout << "Paid " << amount << " via Credit Card\n";
    }
};

class PayPalPayment : public PaymentStrategy {
public:
    void pay(int amount) override {
        std::cout << "Paid " << amount << " via PayPal\n";
    }
};

// Konteks
class ShoppingCart {
    std::unique_ptr<PaymentStrategy> strategy;
public:
    void setPaymentMethod(std::unique_ptr<PaymentStrategy> s) {
        strategy = std::move(s);
    }
    
    void checkout(int total) {
        if (strategy) strategy->pay(total);
    }
};

int main() {
    ShoppingCart cart;
    
    cart.setPaymentMethod(std::make_unique<CreditCardPayment>());
    cart.checkout(100);
    
    cart.setPaymentMethod(std::make_unique<PayPalPayment>());
    cart.checkout(50);
}

ShoppingCart tidak tahu metode pembayaran mana yang digunakannya. ShoppingCart hanya memanggil pay() pada strategi yang ditetapkan. Kamu dapat mengganti strategi saat program berjalan dengan setPaymentMethod(), sehingga sistem menjadi fleksibel dan mudah diperluas dengan opsi pembayaran baru.

Gunakan Strategy saat kamu memiliki beberapa algoritma untuk tugas tertentu dan ingin beralih di antara algoritma tersebut secara dinamis, atau saat kamu ingin menghindari pernyataan percabangan untuk memilih perilaku.

challenge icon

Tantangan

Mudah

Mari buat Kalkulator Pengiriman yang menggunakan pola Strategy untuk menghitung biaya pengiriman berdasarkan berbagai metode pengiriman. Ini adalah skenario praktis ketika kamu perlu mengganti algoritma saat program berjalan: paket yang sama mungkin dikirim melalui darat, udara, atau ekspres, masing-masing dengan logika harganya sendiri.

Kamu akan menyusun kodemu dalam tiga file:

  • ShippingStrategy.h: Definisikan antarmuka strategy dan strategy pengiriman konkret.

    Buat class abstrak ShippingStrategy dengan method virtual murni calculateCost(double weight) yang mengembalikan biaya pengiriman sebagai double, serta destructor virtual.

    Lalu implementasikan tiga strategy konkret:

    • GroundShipping: biayanya 1.5 per satuan berat (weight * 1.5)
    • AirShipping: biayanya 4.0 per satuan berat (weight * 4.0)
    • ExpressShipping: biayanya 6.5 per satuan berat ditambah biaya tetap sebesar 10.0 (weight * 6.5 + 10.0)
  • ShippingService.h: Buat class konteks yang menggunakan strategy pengiriman.

    Class ShippingService milikmu harus menyimpan std::unique_ptr<ShippingStrategy> sebagai member privat. Implementasikan:

    • Method setStrategy(std::unique_ptr<ShippingStrategy> strategy) untuk mengganti metode pengiriman
    • Method calculateShipping(double weight) yang menggunakan strategy saat ini untuk menghitung dan mengembalikan biayanya

    Jika belum ada strategy yang ditetapkan saat calculateShipping dipanggil, kembalikan 0.0.

  • main.cpp: Tunjukkan cara mengganti strategy saat program berjalan.

    Baca dua input:

    1. Berat paket (double)
    2. Metode pengiriman: ground, air, atau express

    Buat ShippingService dan tetapkan strategy yang sesuai berdasarkan metode input. Hitung dan cetak biaya pengiriman.

    Lalu ganti dengan strategy yang berbeda (gunakan air jika inputnya bukan air, jika tidak, gunakan ground) dan hitung kembali biayanya untuk berat yang sama. Ini menunjukkan manfaat mengganti strategy saat program berjalan.

    Cetak setiap biaya pada baris tersendiri dengan tepat satu angka desimal, diawali dengan nama metode:

    [Method]: $[cost]

Contohnya, dengan input 5.0 dan ground:

Ground: $7.5
Air: $20.0

Dengan input 3.0 dan express:

Express: $29.5
Air: $12.0

Dengan input 10.0 dan air:

Air: $40.0
Ground: $15.0

Perhatikan bahwa ShippingService tidak perlu mengetahui detail setiap algoritma penetapan harga. Class ini cukup mendelegasikan tugas kepada strategy yang sedang ditetapkan. Kamu bisa dengan mudah menambahkan metode pengiriman baru (seperti pengiriman dengan drone atau pengiriman di hari yang sama) tanpa mengubah class layanan sama sekali.

Coba sendiri

#include <iostream>
#include <string>
#include <iomanip>
#include <memory>
#include "ShippingStrategy.h"
#include "ShippingService.h"

int main() {
    double weight;
    std::string method;
    
    std::cin >> weight;
    std::cin >> method;
    
    // Atur output agar menampilkan 1 angka di belakang koma
    std::cout << std::fixed << std::setprecision(1);
    
    ShippingService service;
    
    // TODO: Berdasarkan method input ("ground", "air", atau "express"):
    // 1. Atur strategi yang sesuai pada service
    // 2. Hitung dan tampilkan biaya dengan format: "[Method]: $[cost]"
    
    // TODO: Ganti ke strategi lain:
    // - Jika input adalah "air", ganti ke GroundShipping
    // - Jika tidak, ganti ke AirShipping
    // Hitung dan tampilkan biaya baru
    
    return 0;
}
quiz iconUji dirimu

Pelajaran ini berisi kuis singkat. Mulai pelajarannya untuk menjawab kuis dan melacak progresmu.

Semua pelajaran di Pemrograman Berorientasi Object

Latihan sendiri: Compiler C++ online