Skip to content
147 changes: 147 additions & 0 deletions Examples/Jalilpour/DeliveryFactory.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,147 @@

namespace Examples.Jalilpour
{
public enum CargoType
{
Air,
Ship,
Train
}

public class DeliveryService
{
public Delivery Create(CargoType cargoType)
{
if (cargoType == CargoType.Air)
{
return new AirDeliveryFactory().CreateDelivery();
}
else if (cargoType == CargoType.Ship)
{
return new ShipDeliveryFactory().CreateDelivery();
}
else if (cargoType == CargoType.Train)
{
return new TrainDeliveryFactory().CreateDelivery();
}
throw new InvalidOperationException();
}
}

public abstract class Delivery
{
public abstract void DeliverCargo();
}

public class AirDelivery : Delivery
{
public override void DeliverCargo()
{
throw new NotImplementedException();
}
}

public class TrainDelivery : Delivery
{
public override void DeliverCargo()
{
throw new NotImplementedException();
}
}

public class ShipDelivery : Delivery
{
public ShipDelivery()
{

}
public ShipDelivery(string origin, string destination)
{

}
public override void DeliverCargo()
{
throw new NotImplementedException();
}
}



public abstract class DeliveryFactory
{
public abstract Delivery CreateDelivery();
}

public class AirDeliveryFactory : DeliveryFactory
{
private static AirDelivery airDelivery;
public override Delivery CreateDelivery()
{
if (airDelivery == null)
airDelivery = new AirDelivery();
return airDelivery;
}
}

public class ShipDeliveryFactory : DeliveryFactory
{
public override Delivery CreateDelivery()
{
return new ShipDelivery("BandarAbbas", "Astarakhan");
}
}

public class TrainDeliveryFactory : DeliveryFactory
{
private static bool hasAlreadyInstance;
public override Delivery CreateDelivery()
{
if (hasAlreadyInstance)
{
init();
return new TrainDelivery();
}
else
{
hasAlreadyInstance = true;
return new TrainDelivery();
}
}
private void init()
{
throw new NotImplementedException();
}
}



/// <summary>
/// Imagine it is a library and we make it as a package. so users or customers,
/// can't change your code, but they want to add a new behavior like Truck. so, how you can solve it.
/// </summary>
public class Truck : Delivery
{
public override void DeliverCargo()
{
Console.WriteLine("Delivering...");
}
}
public static class DeliveryFactoryExtentionMethod
{
public static void DeliverCargoByTruck(this Delivery truck)
{
throw new NotImplementedException();
}
}
///


public class Program()
{
public void main()
{
Truck truck = new();
truck.DeliverCargoByTruck();
}
}
}
91 changes: 91 additions & 0 deletions Payment/Ecommerce.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Security.Cryptography;
using System.Text;
using System.Threading.Tasks;

namespace Payment
{
public enum PaymetType
{
CreditCard,
PayPal,
CryptoCurrency
}
public class Ecommerce
{
public void Pay(PaymetType paymetType, decimal amount)
{
switch (paymetType)
{
case PaymetType.CreditCard:
new CreditCardProcessor().Pay(amount);
break;
case PaymetType.PayPal:
new PayPalProcessor().Pay(amount);
break;
case PaymetType.CryptoCurrency:
new CryptoAdapter(new CryptoCurrencyProcessor()).Pay(amount);
break;
default: throw new Exception("NullPaymentProcessor");
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

you have to add null object pattern here.

}
}


interface IPaymentProcessor
{
public void Pay(decimal amount);
}

public class CreditCardProcessor : IPaymentProcessor
{
public void Pay(decimal amonut)
{
Console.WriteLine(amonut + (2 * amonut / 100));
}
}

public class PayPalProcessor : IPaymentProcessor
{
public void Pay(decimal amonut)
{
throw new NotImplementedException();
}
}


// Supppose this class comes from a third party library
#region CryptoCurrencyProcessor
public interface ICryptoCurrencyProcessor
{
public bool PayByCrypto(decimal amount);
}
public class CryptoCurrencyProcessor : ICryptoCurrencyProcessor
{
public bool PayByCrypto(decimal amonut)
{
throw new NotImplementedException();
}
}
#endregion


// The CryptoAdapter makes the CryptoCurrencyProcessor compatible with the PaymentProcessor interface
class CryptoAdapter : IPaymentProcessor
{
private readonly CryptoCurrencyProcessor _cryptoCurrencyProcessor;

public CryptoAdapter(CryptoCurrencyProcessor cryptoCurrencyProcessor)
{
_cryptoCurrencyProcessor = cryptoCurrencyProcessor;
}

public void Pay(decimal amonut)
{
_cryptoCurrencyProcessor.PayByCrypto(amonut);
}
}

}
}