shopkeeper/korean_wiki_content_only_120125 huggingface dataset:
public abstract void buildTopping();
public void buildDough() {
pizza.setDough("cross");
public void buildSauce() {
pizza.setSauce("mild");
public void buildTopping() {
pizza.setTopping("ham+pineapple");
pizza.setDough("pan baked");
pizza.setSauce("hot");
pizza.setTopping("pepperoni+salami");
/** "Director" */
class Cook {
public void setPizzaBuilder(PizzaBuilder pizzaBuilder) {
this.pizzaBuilder = pizzaBuilder;
return pizzaBuilder.getPizza();
public void constructPizza() {
pizzaBuilder.createNewPizzaProduct();
pizzaBuilder.buildDough();
pizzaBuilder.buildSauce();
pizzaBuilder.buildTopping();
/** A given type of pizza being constructed. */
public class BuilderExample {
Cook cook = new Cook();
PizzaBuilder hawaiianPizzaBuilder = new HawaiianPizzaBuilder();
PizzaBuilder spicyPizzaBuilder = new SpicyPizzaBuilder();
cook.setPizzaBuilder(hawaiianPizzaBuilder);
cook.constructPizza();
Pizza pizza = cook.getPizza();
//Implementation in C#.
class Pizza
string dough;
string sauce;
string topping;
//Abstract Builder
abstract class PizzaBuilder
public abstract void BuildDough();
public abstract void BuildSauce();
public abstract void BuildTopping();
//Concrete Builder
class HawaiianPizzaBuilder : PizzaBuilder
class SpicyPizzaBuilder : PizzaBuilder
public void ConstructPizza() {
pizzaBuilder.CreateNewPizza();
pizzaBuilder.BuildDough();
pizzaBuilder.BuildSauce();
pizzaBuilder.BuildTopping();
class BuilderExample
public static void Main(string[] args) {
Waiter waiter = new Waiter();
waiter.SetPizzaBuilder ( hawaiianPizzaBuilder );
waiter.ConstructPizza();
Pizza pizza = waiter.GetPizza();
// Implementation in C++.
// Product
std::string dough;
std::string sauce;
std::string topping;
void SetDough(const std::string&amp; d) { dough = d; };
void SetSauce(const std::string&amp; s) { sauce = s; };
void ShowPizza()
std::cout « " Yummy !!!" « std::endl
« "Pizza with Dough as " « dough
« ", Sauce as " « sauce
« " and Topping as " « topping
« " !!! " « std::endl;
// Abstract Builder
class PizzaBuilder
std::auto_ptr&lt;Pizza&gt; pizza;
virtual void buildDough()=0;
virtual void buildSauce()=0;
virtual void buildTopping()=0;
// ConcreteBuilder
class HawaiianPizzaBuilder : public PizzaBuilder
class SpicyPizzaBuilder : public PizzaBuilder
// Director
class Waiter
PizzaBuilder* pizzaBuilder;
void ConstructPizza()
pizzaBuilder-&gt;createNewPizzaProduct();
pizzaBuilder-&gt;buildDough();
pizzaBuilder-&gt;buildSauce();
pizzaBuilder-&gt;buildTopping();
// A customer ordering a pizza.
Waiter waiter;
HawaiianPizzaBuilder hawaiianPizzaBuilder;
waiter.SetPizzaBuilder (&amp;hawaiianPizzaBuilder);
std::auto_ptr&lt;Pizza&gt; pizza = waiter.GetPizza();
pizza-&gt;ShowPizza();
SpicyPizzaBuilder spicyPizzaBuilder;
waiter.SetPizzaBuilder(&amp;spicyPizzaBuilder);
pizza = waiter.GetPizza();
비주얼 프롤로그.
interface pizza
setDough : (string Dough).
setSauce : (string Sauce).
setTopping : (string Topping).
end interface pizza
class pizza : pizza
end class pizza
implement pizza
dough : string := "".
sauce : string := "".
topping : string := "".
setDough(Dough) :- dough := Dough.
setSauce(Sauce) :- sauce := Sauce.
setTopping(Topping) :- topping := Topping.
end implement pizza
Abstract Builder
interface pizzaBuilder
getPizza : () -&gt; pizza Pizza.
createNewPizzaProduct : ().
buildDough : ().
buildSauce : ().
buildTopping : ().
end interface pizzaBuilder
Visual Prolog does not support abstract classes, but we can create a support class instead:
interface pizzaBuilderSupport
predicates from pizzaBuilder
getPizza, createNewPizzaProduct
end interface pizzaBuilderSupport
class pizzaBuilderSupport : pizzaBuilderSupport
end class pizzaBuilderSupport
implement pizzaBuilderSupport
pizza : pizza := erroneous.
getPizza() = pizza.
createNewPizzaProduct() :- pizza := pizza::new().
end implement pizzaBuilderSupport
ConcreteBuilder #1
class hawaiianPizzaBuilder : pizzaBuilder
end class hawaiianPizzaBuilder
implement hawaiianPizzaBuilder
inherits pizzaBuilderSupport
buildDough() :- getPizza():setDough("cross").
buildSauce() :- getPizza():setSauce("mild").
buildTopping() :- getPizza():setTopping("ham+pineapple").
end implement hawaiianPizzaBuilder
ConcreteBuilder #2
class spicyPizzaBuilder : pizzaBuilder
end class spicyPizzaBuilder
implement spicyPizzaBuilder
buildDough() :- getPizza():setDough("pan baked").
buildSauce() :- getPizza():setSauce("hot").
buildTopping() :- getPizza():setTopping("pepperoni+salami").
end implement spicyPizzaBuilder
interface waiter
setPizzaBuilder : (pizzaBuilder PizzaBuilder).
constructPizza : ().
end interface waiter
class waiter : waiter
end class waiter
implement waiter
pizzaBuilder : pizzaBuilder := erroneous.
setPizzaBuilder(PizzaBuilder) :- pizzaBuilder := PizzaBuilder.
getPizza() = pizzaBuilder:getPizza().
constructPizza() :-
pizzaBuilder:createNewPizzaProduct(),
pizzaBuilder:buildDough(),
pizzaBuilder:buildSauce(),
pizzaBuilder:buildTopping().
end implement waiter
A customer ordering a pizza.
Hawaiian_pizzabuilder = hawaiianPizzaBuilder::new(),
Waiter = waiter::new(),
Waiter:setPizzaBuilder(Hawaiian_pizzabuilder),
Waiter:constructPizza(),
Pizza = Waiter:getPizza().
package pizza;
return bless {
dough =&gt; undef,
sauce =&gt; undef,
topping =&gt; undef
}, shift;
sub set_dough {
my( $self, $dough ) = @_;
$self-&gt;{dough} = $dough;
sub set_sauce {
my( $self, $sauce ) = @_;
$self-&gt;{sauce} = $sauce;
sub set_topping {
my( $self, $topping ) = @_;
$self-&gt;{topping} = $topping;
package pizza_builder;
pizza =&gt; undef
sub get_pizza {
my( $self ) = @_;
return $self-&gt;{pizza};
sub create_new_pizza_product {
$self-&gt;{pizza} = pizza-&gt;new;
sub build_dough {
croak("This method must be overridden.");
sub build_sauce {
sub build_topping {
package hawaiian_pizza_builder;
use base qw{ pizza_builder };
$self-&gt;{pizza}-&gt;set_dough("cross");
$self-&gt;{pizza}-&gt;set_sauce("mild");
$self-&gt;{pizza}-&gt;set_topping("ham+pineapple");
package spicy_pizza_builder;
$self-&gt;{pizza}-&gt;set_dough("pan baked");
$self-&gt;{pizza}-&gt;set_sauce("hot");
$self-&gt;{pizza}-&gt;set_topping("pepperoni+salami");
package waiter;
pizza_builder =&gt; undef
sub set_pizza_builder {
my( $self, $builder ) = @_;
$self-&gt;{pizza_builder} = $builder;
return $self-&gt;{pizza_builder}-&gt;get_pizza;
sub construct_pizza {
$self-&gt;{pizza_builder}-&gt;create_new_pizza_product;
$self-&gt;{pizza_builder}-&gt;build_dough;
$self-&gt;{pizza_builder}-&gt;build_sauce;
$self-&gt;{pizza_builder}-&gt;build_topping;
my $waiter = waiter-&gt;new;
my $hawaiian_pb = hawaiian_pizza_builder-&gt;new;
my $spicy_pb = spicy_pizza_builder-&gt;new;
$waiter-&gt;set_pizza_builder( $hawaiian_pb );
$waiter-&gt;construct_pizza;
my $pizza = $waiter-&gt;get_pizza;
print "Serving a nice pizza with:\n";
for (keys %$pizza) {
print " $pizza-&gt;{$_} $_\n";
/** Product **/
class Pizza{
private $dough;
private $sauce;
private $topping;
public function setDough($dough){
$this-&gt;dough = $dough;
public function setSauce($sauce){
$this-&gt;sauce = $sauce;
public function setTopping($topping){
$this-&gt;topping = $topping;
/** Abstract builder **/
abstract class PizzaBuilder{
protected $pizza;
public function __construct(){
$this-&gt;pizza = new Pizza();
public function getPizza(){
return $this-&gt;pizza;
abstract function buildDough();
abstract function buildSauce();
abstract function buildTopping();
/** Concrete builder **/
class SpicyPizza extends PizzaBuilder{
public function buildDough(){
$this-&gt;pizza-&gt;setDough('crispy');
public function buildSauce(){
$this-&gt;pizza-&gt;setSauce('hot');
public function buildTopping(){
$this-&gt;pizza-&gt;setTopping('pepperoni+salami');
/** Director **/
class Chef{
private $pizza_builder;
public function setPizzaBuilder(PizzaBuilder $pizza_builder){
$this-&gt;pizza_builder = $pizza_builder;
public function cookPizza(){
$this-&gt;pizza_builder-&gt;buildDough();
$this-&gt;pizza_builder-&gt;buildSauce();
$this-&gt;pizza_builder-&gt;buildTopping();
return $this-&gt;pizza_builder-&gt;getPizza();
//Customer orders a Pizza.
$chef = new Chef();
$order = new SpicyPizza();
$chef-&gt;setPizzaBuilder($order);
$chef-&gt;cookPizza();
$pizza = $chef-&gt;getPizza();
print_r($pizza);
팩토리 메서드 패턴()은 객체지향 디자인 패턴이다. Factory method는 부모(상위) 클래스에 알려지지 않은 구체 클래스를 생성하는 패턴이며. 자식(하위) 클래스가 어떤 객체를 생성할지를 결정하도록 하는 패턴이기도 하다. 부모(상위) 클래스 코드에 구체 클래스 이름을 감추기 위한 방법으로도 사용한다.
Factory Method라는 패턴 이름이 적절하지 못한데, 이름으로 인해 객체를 생성하는 메소드를 Factory method라 오해하는 개발자가 많이 있다(Allen Holub의 말을 인용.) 이런 생성 메소드가 모두 Factory method 패턴을 사용하는 것은 아니다. Template Method의 생성 패턴 버전으로 볼 수 있는데 Template Method를 알지 못한다면 그 패턴을 먼저 이해하는 것이 Factory Method를 이해하기 수월할 것이다.
Factory Method가 중첩되기 시작하면 굉장히 복잡해 질 수 있다. 또한 상속을 사용하지만 부모(상위) 클래스를 전혀 확장하지 않는다. 따라서 이 패턴은 extends 관계를 잘못 이용한 것으로 볼 수 있다. extends 관계를 남발하게 되면 프로그램의 엔트로피가 높아질 수 있으므로 Factory Method 패턴의 사용을 주의해야 한다.
Pizza example:
public abstract class Pizza
public abstract decimal GetPrice();
public enum PizzaType
HamMushroom, Deluxe, Seafood
public static Pizza PizzaFactory(PizzaType pizzaType)
switch (pizzaType)
case PizzaType.HamMushroom:
return new HamAndMushroomPizza();
case PizzaType.Deluxe:
return new DeluxePizza();
case PizzaType.Seafood:
return new SeafoodPizza();
throw new System.NotSupportedException("The pizza type " + pizzaType.ToString() + " is not recognized.");
public class HamAndMushroomPizza : Pizza
private decimal price = 8.5M;
public class DeluxePizza : Pizza
private decimal price = 10.5M;
public class SeafoodPizza : Pizza
private decimal price = 11.5M;
// Somewhere in the code
Console.WriteLine( Pizza.PizzaFactory(Pizza.PizzaType.Seafood).GetPrice().ToString("C2") ); // $11.50
//Our pizzas
function HamAndMushroomPizza(){
var price = 8.50;
this.getPrice = function(){
return price;
function DeluxePizza(){
var price = 10.50;
function SeafoodPizza(){
var price = 11.50;
//Pizza Factory
function PizzaFactory(){
this.createPizza = function(type){
switch(type){
case "Ham and Mushroom":
case "DeluxePizza":
case "Seafood Pizza":
//Usage
var pizzaPrice = new PizzaFactory().createPizza("Ham and Mushroom").getPrice();
alert(pizzaPrice);
class HamAndMushroomPizza
def price
class DeluxePizza
10.50
class SeafoodPizza
class PizzaFactory
def create_pizza(style=")
case style
when 'Ham and Mushroom'
HamAndMushroomPizza.new
when 'DeluxePizza'
DeluxePizza.new
when 'Seafood Pizza'
SeafoodPizza.new
factory = PizzaFactory.new
pizza = factory.create_pizza('Ham and Mushroom')
pizza.price #=&gt; 8.5
formatted_price = sprintf("$%.2f", pizza.price) #=&gt; "$8.50"
sprintf("$%.2f", PizzaFactory.new.create_pizza('Ham and Mushroom').price) #=&gt; "$8.50"
class Pizza:
HAM_MUSHROOM_PIZZA_TYPE = 0
DELUXE_PIZZA_TYPE = 1
SEAFOOD_PIZZA_TYPE= 2
self.__price = None
def getPrice(self):
return self.__price
class HamAndMushroomPizza(Pizza):
self.__price = 8.50
class DeluxePizza(Pizza):
self.__price = 10.50
class SeafoodPizza(Pizza):
self.__price = 11.50
class PizzaFactory:
def createPizza(self, pizzaType):
if pizzaType == Pizza.HAM_MUSHROOM_PIZZA_TYPE:
return HamAndMushroomPizza()
elif pizzaType == Pizza.DELUXE_PIZZA_TYPE:
return DeluxePizza()
elif pizzaType == Pizza.SEAFOOD_PIZZA_TYPE:
return SeafoodPizza()
pizzaPrice = PizzaFactory().createPizza(Pizza.HAM_MUSHROOM_PIZZA_TYPE).getPrice()
print "$%.02f" % pizzaPrice
소프트웨어 디자인 패턴에서 싱글턴 패턴(Singleton pattern)을 따르는 클래스는, 생성자가 여러 차례 호출되더라도 실제로 생성되는 객체는 하나이고 최초 생성 이후에 호출된 생성자는 최초의 생성자가 생성한 객체를 리턴한다. 이와 같은 디자인 유형을 싱글턴 패턴이라고 한다. 주로 공통된 객체를 여러개 생성해서 사용하는 DBCP(DataBase Connection Pool)와 같은 상황에서 많이 사용된다.
언어별 구현.
private static Coin instance = new Coin(); // eagerly loads the singleton
private Coin() {
public static Coin getInstance() {
public int getCoin() {
public void addMoreCoin() {
public void deductCoin() {
class Singleton:
__instance = None
def __new__(cls, *args):
if cls.__instance is None:
cls.__instance = object.__new__(cls, *args)
return cls.__instance
static Singleton&amp; GetInstance() {
// Allocate with `new` in case Singleton is not trivially destructible.
static Singleton* singleton = new Singleton();
return *singleton;
Singleton() = default;
// Delete copy/move so extra instances can't be created/moved.
Singleton(const Singleton&amp;) = delete;
Singleton&amp; operator=(const Singleton&amp;) = delete;
Singleton(Singleton&amp;&amp;) = delete;
Singleton&amp; operator=(Singleton&amp;&amp;) = delete;
public sealed class Singleton
private static volatile Singleton? _instance;
private static readonly object _lock = new object();
public static Singleton Instance
if (_instance != null)
return _instance;
lock (_lock)
if (_instance == null)
_instance = new Singleton();
public static class Singleton
public static MyOtherClass Instance { get; } = new MyOtherClass();
유니티.
class Singleton : MonoBehaviour
private void Awake()
if (Instance != null &amp;&amp; Instance != this)
Destroy(this.gameObject);
Instance = this;
다트.
Singleton._();
static final Singleton _instance = Singleton._();
static Singleton get instance =&gt; _instance;
class Singleton
코틀린.
object Coin {
fun getCoin():Int {
fun addCoin() {
fun deductCoin() {
var instance *Singleton
func GetInstance() *Singleton {
if instance != nil {
instance = new(Singleton)
오브젝트 어댑터.
class Target(object):
def specific_request(self):
return 'Hello Adapter Pattern!'
class Adapter(object):
def __init__(self, adaptee):
self.adaptee = adaptee
def request(self):
return self.adaptee.specific_request()
client = Adapter(Target())
print client.request()
클래스 어댑터.
* Java code sample
/* the client class should instantiate adapter objects */
/* by using a reference of this type */
interface Stack&lt;T&gt;
void push (T o);
T pop ();
T top ();
/* DoubleLinkedList is the adaptee class */
class DList&lt;T&gt;
/* Adapt DList class to Stack interface is the adapter class */
class DListImpStack&lt;T&gt; extends DList&lt;T&gt; implements Stack&lt;T&gt;
public void push (T o) {
insertTail (o);
public T pop () {
return removeTail ();
public T top () {
return getTail ();
코드 예.
public void draw(); // low-level
public void resizeByPercentage(double pct); // high-level
this.x = x; this.y = y; this.radius = radius;
public void draw()
Shape[] shapes = new Shape[2];
shapes[0] = new CircleShape(1, 2, 3, new DrawingAPI1());
shapes[1] = new CircleShape(5, 7, 11, new DrawingAPI2());
shape.draw();
void Draw(); // low-level (i.e. Implementation-specific)
void ResizeByPercentage(double pct); // high-level (i.e. Abstraction-specific)
IShape[] shapes = new IShape[2];
shape.Draw();
virtual ~DrawingAPI(){};
cout « "API1.circle at " « x « ":" « y « " " « radius « endl;
/* Concrete ImplementorB*/
class DrawingAPI2 : public DrawingAPI {
cout « "API2.circle at " « x « ":" « y « " " « radius « endl;
/* Abstraction*/
virtual ~Shape() {};
virtual void draw() = 0;
virtual void resizeByPercentage(double pct) = 0;
/* Refined Abstraction*/
class CircleShape : public Shape {
CircleShape(double x, double y,double radius, DrawingAPI *drawingAPI){
m_x = x;
m_y = y;
m_radius = radius;
m_drawingAPI = drawingAPI;
m_drawingAPI-&gt;drawCircle(m_x,m_y,m_radius);
double m_x,m_y,m_radius;
CircleShape circle1(1,2,3,&amp;dap1);
CircleShape circle2(5,7,11,&amp;dap2);
circle1.draw();
circle2.draw();
// Implementor
type DrawingAPI interface {
drawCircle(float32, float32, float32)
// ConcreteImplementor 1/2
func (d *DrawingAPI1) drawCircle(x float32, y float32, radius float32) {
fmt.Printf("API1.circle at %f:%f radius %f\n", x, y, radius)
// ConcreteImplementor 2/2
func (d *DrawingAPI2) drawCircle(x float32, y float32, radius float32) {
fmt.Printf("API2.circle at %f:%f radius %f\n", x, y, radius)
// Abstraction
type Shape interface {
resizeByPercentage(float32)
// Refined Abstraction
type CircleShape struct {
x, y, radius float32
drawingAPI DrawingAPI
// Implementation specific
func (c *CircleShape) draw() {
c.drawingAPI.drawCircle(c.x, c.y, c.radius)
// Abstraction specific
func (c *CircleShape) resizeByPercentage(pct float32) {
c.radius *= pct
// Client
shape1.resizeByPercentage(2.5)
shape1.draw()
shape2.resizeByPercentage(2)
shape2.draw()
def draw_circle(self, x, y, radius):
print(f"API1.circle at {x}:{y} {radius}")
print(f"API2.circle at {x}:{y} {radius}")
def resize_by_percentage(pct):
radius = 0
drawing_api = None
def __init__(self, x, y, radius, drawing_api):
self.x = x
self.y = y
self.radius = radius
self.drawing_api = drawing_api
self.drawing_api.draw_circle(self.x, self.y, self.radius)
def resize_by_percentage(self, pct):
self.radius *= pct
dap1 = DrawingAPI1()
dap2 = DrawingAPI2()
circle1 = CircleShape(1, 2, 3, dap1)
circle2 = CircleShape(5, 7, 11, dap2)
circle1.resize_by_percentage(2.5)
circle2.resize_by_percentage(2.5)
circle1.draw()
circle2.draw()
/** "Component" */
interface Graphic {
//Prints the graphic.
public void print();
/** "Composite" */
class CompositeGraphic implements Graphic {
//Collection of child graphics.
private List&lt;Graphic&gt; mChildGraphics = new ArrayList&lt;Graphic&gt;();
public void print() {
for (Graphic graphic : mChildGraphics) {
graphic.print();
//Adds the graphic to the composition.
public void add(Graphic graphic) {
mChildGraphics.add(graphic);
//Removes the graphic from the composition.
public void remove(Graphic graphic) {
mChildGraphics.remove(graphic);
/** "Leaf" */
class Ellipse implements Graphic {
System.out.println("Ellipse");
/** Client */
public class Program {
//Initialize four ellipses
Ellipse ellipse1 = new Ellipse();
Ellipse ellipse2 = new Ellipse();
Ellipse ellipse3 = new Ellipse();
Ellipse ellipse4 = new Ellipse();
//Initialize three composite graphics
CompositeGraphic graphic = new CompositeGraphic();
CompositeGraphic graphic1 = new CompositeGraphic();
CompositeGraphic graphic2 = new CompositeGraphic();
//Composes the graphics
graphic1.add(ellipse1);
graphic1.add(ellipse2);
graphic1.add(ellipse3);
graphic2.add(ellipse4);
graphic.add(graphic1);
graphic.add(graphic2);
//Prints the complete graphic (four times the string "Ellipse").
using std::vector;
using std::string;
class Component
virtual void list() const = 0;
virtual ~Component(){};
class Leaf : public Component
explicit Leaf(int val) : value_(val)
void list() const
cout « " " « value_ « "\n";
int value_;
class Composite : public Component
explicit Composite(string id) : id_(id)
void add(Component *obj)
table_.push_back(obj);
cout « id_ « ":" « "\n";
for (vector&lt;Component*&gt;::const_iterator it = table_.begin();
it != table_.end(); ++it)
(*it)-&gt;list();
vector &lt;Component*&gt; table_;
string id_;
Leaf num0(0);
Leaf num1(1);
Leaf num2(2);
Leaf num3(3);
Leaf num4(4);
Composite container1("Container 1");
Composite container2("Container 2");
container1.add(&amp;num0);
container1.add(&amp;num1);
container2.add(&amp;num2);
container2.add(&amp;num3);
container2.add(&amp;num4);
container1.add(&amp;container2);
container1.list();
from abc import abstractmethod
class Component:
def my_list(self):
class Leaf(Component):
val = None
def __init__(self, val) -&gt; None:
super().__init__()
self.val = val
print(self.val)
class Composite(Component):
composite_list = None
def add(self, obj):
if not self.composite_list:
self.composite_list = []
self.composite_list.append(obj)
print(self.val, ":")
for obj in self.composite_list:
obj.my_list()
num0 = Leaf(0)
num1 = Leaf(1)
num2 = Leaf(2)
num3 = Leaf(3)
num4 = Leaf(4)
container1 = Composite("Container 1")
container2 = Composite("Container 2")
container1.add(num0)
container1.add(num1)
container2.add(num2)
container2.add(num3)
container2.add(num4)
container1.add(container2)
container1.my_list()
// the Window interface
interface Window {
public void draw(); // draws the Window
public String getDescription(); // returns a description of the Window
class SimpleWindow implements Window {
public void draw() {
// draw window
public String getDescription() {
abstract class WindowDecorator implements Window {
// the first concrete decorator which adds vertical scrollbar functionality
class VerticalScrollBarDecorator extends WindowDecorator {
public VerticalScrollBarDecorator (Window decoratedWindow) {
super(decoratedWindow);
drawVerticalScrollBar();
decoratedWindow.draw();
private void drawVerticalScrollBar() {
// draw the vertical scrollbar
return decoratedWindow.getDescription() + ", including vertical scrollbars";
// the second concrete decorator which adds horizontal scrollbar functionality
class HorizontalScrollBarDecorator extends WindowDecorator {
public HorizontalScrollBarDecorator (Window decoratedWindow) {
drawHorizontalScrollBar();
private void drawHorizontalScrollBar() {
// draw the horizontal scrollbar
return decoratedWindow.getDescription() + ", including horizontal scrollbars";
public class DecoratedWindowTest {
// create a decorated Window with horizontal and vertical scrollbars
Window decoratedWindow = new HorizontalScrollBarDecorator (
new VerticalScrollBarDecorator(new SimpleWindow()));
// print the Window's description
System.out.println(decoratedWindow.getDescription());
width = w;
cout « "TextField: " « width « ", " « height « '\n';
/* Decorator (interface) */
class Decorator : public Widget {
Widget* wid; // reference to Widget
Decorator( Widget* w ) {
wid = w;
wid-&gt;draw();
~Decorator() {
Decorator::draw();
cout « " BorderDecorator" « '\n';
/* ConcreteDecoratorB */
class ScrollDecorator : public Decorator {
cout « " ScrollDecorator" « '\n';
int main( void ) {
Widget* aWidget = new BorderDecorator(
new ScrollDecorator(
new TextField( 80, 24 )));
aWidget-&gt;draw();
플라이웨이트 패턴()는 동일하거나 유사한 객체들 사이에 가능한 많은 데이터를 서로 공유하여 사용하도록 하여 메모리 사용량을 최소화하는 소프트웨어 디자인 패턴이다. 종종 오브젝트의 일부 상태 정보는 공유될 수 있는데, 플라이웨이트 패턴에서는 이와 같은 상태 정보를 외부 자료 구조에 저장하여 플라이웨이트 오브젝트가 잠깐 동안 사용할 수 있도록 전달한다.
private static final WeakHashMap&lt;FontData, WeakReference&lt;FontData» flyweightData =
new WeakHashMap&lt;FontData, WeakReference&lt;FontData»();
private final Set&lt;FontEffect&gt; effects;
private FontData(int pointSize, String fontFace, Color color, EnumSet&lt;FontEffect&gt; effects) {
EnumSet&lt;FontEffect&gt; effectsSet = EnumSet.noneOf(FontEffect.class);
if (!flyweightData.containsKey(data)) {
flyweightData.put(data, new WeakReference(data));
return flyweightData.get(data).get();
return other.pointSize == pointSize &amp;&amp; other.fontFace.equals(fontFace)
&amp;&amp; other.color.equals(color) &amp;&amp; other.effects.equals(effects);
public int hashCode() {
return (pointSize * 37 + effects.hashCode() * 13) * fontFace.hashCode();
class GraphicChar {
string fontFace;
public static void printAtPosition(GraphicChar c, int x, int y) {
Console.WriteLine("Printing '{0}' in '{1}' at position {2}:{3}.", c.c, c.fontFace, x, y);
class GraphicCharFactory {
Hashtable pool = new Hashtable(); // the Flyweights
public GraphicChar get(char c, string fontFace) {
GraphicChar gc;
string key = c.ToString() + fontFace;
gc = pool[key] as GraphicChar;
if (gc == null) {
gc = new GraphicChar(c, fontFace);
pool.Add(key, gc);
return gc;
class FlyWeightExample {
GraphicCharFactory cf = new GraphicCharFactory();
// Compose the text by storing the characters as objects.
List&lt;GraphicChar&gt; text = new List&lt;GraphicChar&gt;();
text.Add(cf.get('H', "Arial")); // 'H' and "Arial" are called intrinsic information
text.Add(cf.get('e', "Arial")); // because it is stored in the object itself.
text.Add(cf.get('l', "Arial"));
text.Add(cf.get('o', "Times"));
// See how the Flyweight approach is beginning to save space:
Console.WriteLine("CharFactory created only {0} objects for {1} characters.", cf.getNum(), text.Count);
int x=0, y=0;
foreach (GraphicChar c in text) { // Passing position as extrinsic information to the objects,
GraphicChar.printAtPosition(c, x++, y); // as a top-left 'A' is not different from a top-right one.
객체 지향 디자인에서 책임 연쇄 패턴(chain-of-responsibility pattern)은 명령 객체와 일련의 처리 객체를 포함하는 디자인 패턴이다. 각각의 처리 객체는 명령 객체를 처리할 수 있는 연산의 집합이고, 체인 안의 처리 객체가 핸들할 수 없는 명령은 다음 처리 객체로 넘겨진다. 이 작동방식은 새로운 처리 객체부터 체인의 끝까지 다시 반복된다.
표준 책임 연쇄 모델이 변화하면서, 어떤 처리 방식에서는 다양한 방향으로 명령을 보내 책임을 트리 형태로 바꾸는 관제사 역할을 하기도 한다. 몇몇 경우에서는, 처리 객체가 상위의 처리 객체와 명령을 호출하여 작은 파트의 문제를 해결하기 위해 재귀적으로 실행된다. 이 경우 재귀는 명령이 처리되거나 모든 트리가 탐색될때까지 진행되게 된다. XML(파싱되었으나 실행되지 않은) 인터프리터가 한 예이다.
아래의 자바코드는 로그를 남겨주는 클래스를 보여준다. 각각의 로그 핸들러들은 로그 레벨과 다음 로그 핸들러로 넘겨주는 기능을 가지고 있다.
Writing to stdout: Entering function y.
Writing to stdout: Step1 completed.
Sending via e-mail: Step1 completed.
Writing to stdout: An error has occurred.
Sending via e-mail: An error has occurred.
Writing to stderr: An error has occurred.
뿐만 아니라, 완벽한 책임 연쇄 패턴을 구현하기 위해서 로거는 메시지를 넘긴 이후 하위 체인으로 메시지를 전달할 수 없다. 이 예에서 메시지가 처리되는지 여부와 관계없이 하위 체인으로 전달된다.
abstract class Logger {