using Newtonsoft.Json;using System;using System.Collections.Generic;using System.Linq;using System.Runtime.InteropServices.ComTypes;using System.Text.Json.Serialization;namespace ConsoleApp1
{classProgram{staticvoidMain(string[] args){// The client code usually creates a bunch of pre-populated// flyweights in the initialization stage of the application.var factory =newFlyweightFactory(newCar{ Company ="Chevrolet", Model ="Camaro2018", Color ="pink"},newCar{ Company ="Mercedes Benz", Model ="C300", Color ="black"},newCar{ Company ="Mercedes Benz", Model ="C500", Color ="red"},newCar{ Company ="BMW", Model ="M5", Color ="red"},newCar{ Company ="BMW", Model ="X6", Color ="white"});
factory.listFlyweights();addCarToPoliceDatabase(factory,newCar{
Number ="CL234IR",
Owner ="James Doe",
Company ="BMW",
Model ="M5",
Color ="red"});addCarToPoliceDatabase(factory,newCar{
Number ="CL234IR",
Owner ="James Doe",
Company ="BMW",
Model ="X1",
Color ="red"});
factory.listFlyweights();}publicstaticvoidaddCarToPoliceDatabase(FlyweightFactory factory,Car car){
Console.WriteLine("\nClient:Adding a car to database");var flyweight = factory.GetFlyweight(newCar{ Color = car.Color,Model = car.Model,Company = car.Company });
flyweight.Operation(car);}}publicclassFlyweight{privateCar _sharedState;publicFlyweight(Car car){this._sharedState = car;}publicvoidOperation(Car uniqueState){string s = JsonConvert.SerializeObject(this._sharedState);string u = JsonConvert.SerializeObject(uniqueState);
Console.WriteLine($"Flyweight:Displaying shared {s} and unique {u} state");}}publicclassFlyweightFactory{private List<Tuple<Flyweight,string>> flyweights =newList<Tuple<Flyweight,string>>();publicFlyweightFactory(params Car[] args){foreach(var elem in args){
flyweights.Add(newTuple<Flyweight,string>(newFlyweight(elem),this.getKey(elem)));}}publicstringgetKey(Car key){
List<string> elements =newList<string>();
elements.Add(key.Model);
elements.Add(key.Color);
elements.Add(key.Company);if(key.Owner !=null&& key.Number !=null){
elements.Add(key.Number);
elements.Add(key.Owner);}
elements.Sort();returnstring.Join("_", elements);}publicFlyweightGetFlyweight(Car sharedState){string key =this.getKey(sharedState);if(flyweights.Where(t => t.Item2 == key).Count()==0){
Console.WriteLine("FlyweightFactory:Can't find a flyweight,creating new one.");this.flyweights.Add(newTuple<Flyweight,string>(newFlyweight(sharedState), key));}else{
Console.WriteLine("FlyweightFactory:Reusing existing flyweight");}returnthis.flyweights.Where(t => t.Item2 == key).FirstOrDefault().Item1;}publicvoidlistFlyweights(){var count = flyweights.Count;
Console.WriteLine($"FlyweightFactory: I Have {count} flyweights\n");foreach(var flyweight in flyweights)
Console.WriteLine(flyweight.Item2);}}publicclassCar{publicstring Owner {get;set;}publicstring Number {get;set;}publicstring Company {get;set;}publicstring Model {get;set;}publicstring Color {get;set;}}}