Compare commits
2 Commits
all-contri
...
all-contri
Author | SHA1 | Date | |
---|---|---|---|
|
be52efc49b | ||
|
e47a24643a |
@@ -1314,42 +1314,6 @@
|
||||
"contributions": [
|
||||
"code"
|
||||
]
|
||||
},
|
||||
{
|
||||
"login": "viveksb007",
|
||||
"name": "Vivek Singh",
|
||||
"avatar_url": "https://avatars1.githubusercontent.com/u/12713808?v=4",
|
||||
"profile": "https://viveksb007.github.io",
|
||||
"contributions": [
|
||||
"code"
|
||||
]
|
||||
},
|
||||
{
|
||||
"login": "siavashsoleymani",
|
||||
"name": "siavash",
|
||||
"avatar_url": "https://avatars2.githubusercontent.com/u/18074419?v=4",
|
||||
"profile": "https://github.com/siavashsoleymani",
|
||||
"contributions": [
|
||||
"code"
|
||||
]
|
||||
},
|
||||
{
|
||||
"login": "ruchpeanuts",
|
||||
"name": "ruchpeanuts",
|
||||
"avatar_url": "https://avatars0.githubusercontent.com/u/29301900?v=4",
|
||||
"profile": "https://github.com/ruchpeanuts",
|
||||
"contributions": [
|
||||
"doc"
|
||||
]
|
||||
},
|
||||
{
|
||||
"login": "warp125",
|
||||
"name": "warp125",
|
||||
"avatar_url": "https://avatars1.githubusercontent.com/u/48073115?v=4",
|
||||
"profile": "https://github.com/warp125",
|
||||
"contributions": [
|
||||
"translation"
|
||||
]
|
||||
}
|
||||
],
|
||||
"contributorsPerLine": 4,
|
||||
|
@@ -10,7 +10,7 @@
|
||||
[](https://sonarcloud.io/dashboard?id=iluwatar_java-design-patterns)
|
||||
[](https://gitter.im/iluwatar/java-design-patterns?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
|
||||
<!-- ALL-CONTRIBUTORS-BADGE:START - Do not remove or modify this section -->
|
||||
[](#contributors-)
|
||||
[](#contributors-)
|
||||
<!-- ALL-CONTRIBUTORS-BADGE:END -->
|
||||
|
||||
# Introduction
|
||||
@@ -285,12 +285,6 @@ This project is licensed under the terms of the MIT license.
|
||||
<td align="center"><a href="https://github.com/omk13"><img src="https://avatars0.githubusercontent.com/u/59054172?v=4" width="100px;" alt=""/><br /><sub><b>Omar Karazoun</b></sub></a><br /><a href="https://github.com/iluwatar/java-design-patterns/commits?author=omk13" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/jeff303"><img src="https://avatars0.githubusercontent.com/u/3521562?v=4" width="100px;" alt=""/><br /><sub><b>Jeff Evans</b></sub></a><br /><a href="https://github.com/iluwatar/java-design-patterns/commits?author=jeff303" title="Code">💻</a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://viveksb007.github.io"><img src="https://avatars1.githubusercontent.com/u/12713808?v=4" width="100px;" alt=""/><br /><sub><b>Vivek Singh</b></sub></a><br /><a href="https://github.com/iluwatar/java-design-patterns/commits?author=viveksb007" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/siavashsoleymani"><img src="https://avatars2.githubusercontent.com/u/18074419?v=4" width="100px;" alt=""/><br /><sub><b>siavash</b></sub></a><br /><a href="https://github.com/iluwatar/java-design-patterns/commits?author=siavashsoleymani" title="Code">💻</a></td>
|
||||
<td align="center"><a href="https://github.com/ruchpeanuts"><img src="https://avatars0.githubusercontent.com/u/29301900?v=4" width="100px;" alt=""/><br /><sub><b>ruchpeanuts</b></sub></a><br /><a href="https://github.com/iluwatar/java-design-patterns/commits?author=ruchpeanuts" title="Documentation">📖</a></td>
|
||||
<td align="center"><a href="https://github.com/warp125"><img src="https://avatars1.githubusercontent.com/u/48073115?v=4" width="100px;" alt=""/><br /><sub><b>warp125</b></sub></a><br /><a href="#translation-warp125" title="Translation">🌍</a></td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
<!-- markdownlint-enable -->
|
||||
|
@@ -1,54 +0,0 @@
|
||||
---
|
||||
layout: pattern
|
||||
title: Data Transfer Object
|
||||
folder: data-transfer-object
|
||||
permalink: /patterns/data-transfer-object/
|
||||
categories: Architectural
|
||||
tags:
|
||||
- Performance
|
||||
---
|
||||
|
||||
## Intent
|
||||
|
||||
Pass data with multiple attributes in one shot from client to server, to avoid multiple calls to
|
||||
remote server.
|
||||
|
||||
## Explanation
|
||||
|
||||
Real world example
|
||||
|
||||
> We need to fetch information about customers from remote database. Instead of querying the
|
||||
> attributes one at a time, we use DTOs to transfer all the relevant attributes in a single shot.
|
||||
|
||||
In plain words
|
||||
|
||||
> Using DTO relevant information can be fetched with a single backend query.
|
||||
|
||||
Wikipedia says
|
||||
|
||||
> In the field of programming a data transfer object (DTO) is an object that carries data between
|
||||
> processes. The motivation for its use is that communication between processes is usually done
|
||||
> resorting to remote interfaces (e.g. web services), where each call is an expensive operation.
|
||||
> Because the majority of the cost of each call is related to the round-trip time between the client
|
||||
> and the server, one way of reducing the number of calls is to use an object (the DTO) that
|
||||
> aggregates the data that would have been transferred by the several calls, but that is served by
|
||||
> one call only.
|
||||
|
||||
## Class diagram
|
||||
|
||||

|
||||
|
||||
## Applicability
|
||||
|
||||
Use the Data Transfer Object pattern when:
|
||||
|
||||
* The client is asking for multiple information. And the information is related.
|
||||
* When you want to boost the performance to get resources.
|
||||
* You want reduced number of remote calls.
|
||||
|
||||
## Credits
|
||||
|
||||
* [Design Pattern - Transfer Object Pattern](https://www.tutorialspoint.com/design_pattern/transfer_object_pattern.htm)
|
||||
* [Data Transfer Object](https://msdn.microsoft.com/en-us/library/ff649585.aspx)
|
||||
* [J2EE Design Patterns](https://www.amazon.com/gp/product/0596004273/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596004273&linkCode=as2&tag=javadesignpat-20&linkId=f27d2644fbe5026ea448791a8ad09c94)
|
||||
* [Patterns of Enterprise Application Architecture](https://www.amazon.com/gp/product/0321127420/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0321127420&linkCode=as2&tag=javadesignpat-20&linkId=014237a67c9d46f384b35e10151956bd)
|
@@ -1,129 +0,0 @@
|
||||
@startuml
|
||||
package com.iluwatar.datatransferenum {
|
||||
class App {
|
||||
- LOGGER : Logger {static}
|
||||
+ App()
|
||||
+ main(args : String[]) {static}
|
||||
}
|
||||
class Product {
|
||||
- cost : Double
|
||||
- id : Long
|
||||
- name : String
|
||||
- price : Double
|
||||
- supplier : String
|
||||
+ Product()
|
||||
+ getCost() : Double
|
||||
+ getId() : Long
|
||||
+ getName() : String
|
||||
+ getPrice() : Double
|
||||
+ getSupplier() : String
|
||||
+ setCost(cost : Double) : Product
|
||||
+ setId(id : Long) : Product
|
||||
+ setName(name : String) : Product
|
||||
+ setPrice(price : Double) : Product
|
||||
+ setSupplier(supplier : String) : Product
|
||||
+ toString() : String
|
||||
}
|
||||
enum ProductDTO {
|
||||
+ valueOf(name : String) : ProductDTO {static}
|
||||
+ values() : ProductDTO[] {static}
|
||||
}
|
||||
-interface Cost {
|
||||
+ getCost() : Double {abstract}
|
||||
}
|
||||
-interface Id {
|
||||
+ getId() : Long {abstract}
|
||||
}
|
||||
-interface Name {
|
||||
+ getName() : String {abstract}
|
||||
}
|
||||
-interface Price {
|
||||
+ getPrice() : Double {abstract}
|
||||
}
|
||||
enum Request {
|
||||
+ valueOf(name : String) : Request {static}
|
||||
+ values() : Request[] {static}
|
||||
}
|
||||
class Create {
|
||||
- cost : Double
|
||||
- name : String
|
||||
- price : Double
|
||||
- supplier : String
|
||||
+ Create()
|
||||
+ getCost() : Double
|
||||
+ getName() : String
|
||||
+ getPrice() : Double
|
||||
+ getSupplier() : String
|
||||
+ setCost(cost : Double) : Create
|
||||
+ setName(name : String) : Create
|
||||
+ setPrice(price : Double) : Create
|
||||
+ setSupplier(supplier : String) : Create
|
||||
}
|
||||
enum Response {
|
||||
+ valueOf(name : String) : Response {static}
|
||||
+ values() : Response[] {static}
|
||||
}
|
||||
class Private {
|
||||
- cost : Double
|
||||
- id : Long
|
||||
- name : String
|
||||
- price : Double
|
||||
+ Private()
|
||||
+ getCost() : Double
|
||||
+ getId() : Long
|
||||
+ getName() : String
|
||||
+ getPrice() : Double
|
||||
+ setCost(cost : Double) : Private
|
||||
+ setId(id : Long) : Private
|
||||
+ setName(name : String) : Private
|
||||
+ setPrice(price : Double) : Private
|
||||
+ toString() : String
|
||||
}
|
||||
class Public {
|
||||
- id : Long
|
||||
- name : String
|
||||
- price : Double
|
||||
+ Public()
|
||||
+ getId() : Long
|
||||
+ getName() : String
|
||||
+ getPrice() : Double
|
||||
+ setId(id : Long) : Public
|
||||
+ setName(name : String) : Public
|
||||
+ setPrice(price : Double) : Public
|
||||
+ toString() : String
|
||||
}
|
||||
-interface Supplier {
|
||||
+ getSupplier() : String {abstract}
|
||||
}
|
||||
class ProductResource {
|
||||
- products : List<Product>
|
||||
+ ProductResource(products : List<Product>)
|
||||
+ getAllProductsForAdmin() : List<Private>
|
||||
+ getAllProductsForCustomer() : List<Public>
|
||||
+ getProducts() : List<Product>
|
||||
+ save(createProductDTO : Create)
|
||||
}
|
||||
}
|
||||
Create ..+ Request
|
||||
Request ..+ ProductDTO
|
||||
Private ..+ Response
|
||||
Supplier ..+ ProductDTO
|
||||
Name ..+ ProductDTO
|
||||
ProductResource --> "-products" Product
|
||||
Public ..+ Response
|
||||
Id ..+ ProductDTO
|
||||
Price ..+ ProductDTO
|
||||
Response ..+ ProductDTO
|
||||
Cost ..+ ProductDTO
|
||||
Create ..|> Name
|
||||
Create ..|> Price
|
||||
Create ..|> Cost
|
||||
Create ..|> Supplier
|
||||
Private ..|> Id
|
||||
Private ..|> Name
|
||||
Private ..|> Price
|
||||
Private ..|> Cost
|
||||
Public ..|> Id
|
||||
Public ..|> Name
|
||||
Public ..|> Price
|
||||
@enduml
|
Binary file not shown.
Before Width: | Height: | Size: 120 KiB |
@@ -1,61 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!--
|
||||
|
||||
The MIT License
|
||||
Copyright © 2014-2019 Ilkka Seppälä
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
|
||||
-->
|
||||
<project xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd" xmlns="http://maven.apache.org/POM/4.0.0">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
<parent>
|
||||
<groupId>com.iluwatar</groupId>
|
||||
<artifactId>java-design-patterns</artifactId>
|
||||
<version>1.24.0-SNAPSHOT</version>
|
||||
</parent>
|
||||
<artifactId>data-transfer-object-enum-impl</artifactId>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.junit.jupiter</groupId>
|
||||
<artifactId>junit-jupiter-engine</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-assembly-plugin</artifactId>
|
||||
<executions>
|
||||
<execution>
|
||||
<configuration>
|
||||
<archive>
|
||||
<manifest>
|
||||
<mainClass>com.iluwatar.datatransferenum.App</mainClass>
|
||||
</manifest>
|
||||
</archive>
|
||||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
</project>
|
@@ -1,59 +0,0 @@
|
||||
package com.iluwatar.datatransferenum;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
/**
|
||||
* The Data Transfer Object pattern is a design pattern in which an data transfer object is used to
|
||||
* serve related information together to avoid multiple call for each piece of information.
|
||||
*
|
||||
* <p>In this example, ({@link App}) as as product details consumer i.e. client to
|
||||
* request for product details to server.
|
||||
*
|
||||
* <p>productResource ({@link ProductResource}) act as server to serve product information. And
|
||||
* The productDto ({@link ProductDto} is data transfer object to share product information.
|
||||
*/
|
||||
public class App {
|
||||
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(App.class);
|
||||
|
||||
/**
|
||||
* Method as act client and request to server for details.
|
||||
*
|
||||
* @param args program argument.
|
||||
*/
|
||||
public static void main(String[] args) {
|
||||
Product tv =
|
||||
new Product().setId(1L).setName("TV").setSupplier("Sony").setPrice(1000D).setCost(1090D);
|
||||
Product microwave =
|
||||
new Product().setId(2L).setName("microwave").setSupplier("Delonghi").setPrice(1000D)
|
||||
.setCost(1090D);
|
||||
Product refrigerator =
|
||||
new Product().setId(3L).setName("refrigerator").setSupplier("Botsch").setPrice(1000D)
|
||||
.setCost(1090D);
|
||||
Product airConditioner =
|
||||
new Product().setId(4L).setName("airConditioner").setSupplier("LG").setPrice(1000D)
|
||||
.setCost(1090D);
|
||||
List<Product> products =
|
||||
new ArrayList<>(Arrays.asList(tv, microwave, refrigerator, airConditioner));
|
||||
ProductResource productResource = new ProductResource(products);
|
||||
|
||||
LOGGER.info("####### List of products including sensitive data just for admins: \n {}",
|
||||
Arrays.toString(productResource.getAllProductsForAdmin().toArray()));
|
||||
LOGGER.info("####### List of products for customers: \n {}",
|
||||
Arrays.toString(productResource.getAllProductsForCustomer().toArray()));
|
||||
|
||||
LOGGER.info("####### Going to save Sony PS5 ...");
|
||||
ProductDto.Request.Create createProductRequestDto = new ProductDto.Request.Create()
|
||||
.setName("PS5")
|
||||
.setCost(1000D)
|
||||
.setPrice(1220D)
|
||||
.setSupplier("Sony");
|
||||
productResource.save(createProductRequestDto);
|
||||
LOGGER.info("####### List of products after adding PS5: {}",
|
||||
Arrays.toString(productResource.getProducts().toArray()));
|
||||
}
|
||||
}
|
@@ -1,91 +0,0 @@
|
||||
package com.iluwatar.datatransferenum;
|
||||
|
||||
/**
|
||||
* {@link Product} is a entity class for product entity. This class act as entity in the demo.
|
||||
*/
|
||||
public final class Product {
|
||||
private Long id;
|
||||
private String name;
|
||||
private Double price;
|
||||
private Double cost;
|
||||
private String supplier;
|
||||
|
||||
/**
|
||||
* Constructor.
|
||||
*
|
||||
* @param id product id
|
||||
* @param name product name
|
||||
* @param price product price
|
||||
* @param cost product cost
|
||||
* @param supplier product supplier
|
||||
*/
|
||||
public Product(Long id, String name, Double price, Double cost, String supplier) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
this.price = price;
|
||||
this.cost = cost;
|
||||
this.supplier = supplier;
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor.
|
||||
*/
|
||||
public Product() {
|
||||
}
|
||||
|
||||
public Long getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public Product setId(Long id) {
|
||||
this.id = id;
|
||||
return this;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public Product setName(String name) {
|
||||
this.name = name;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Double getPrice() {
|
||||
return price;
|
||||
}
|
||||
|
||||
public Product setPrice(Double price) {
|
||||
this.price = price;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Double getCost() {
|
||||
return cost;
|
||||
}
|
||||
|
||||
public Product setCost(Double cost) {
|
||||
this.cost = cost;
|
||||
return this;
|
||||
}
|
||||
|
||||
public String getSupplier() {
|
||||
return supplier;
|
||||
}
|
||||
|
||||
public Product setSupplier(String supplier) {
|
||||
this.supplier = supplier;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "Product{"
|
||||
+ "id=" + id
|
||||
+ ", name='" + name + '\''
|
||||
+ ", price=" + price
|
||||
+ ", cost=" + cost
|
||||
+ ", supplier='" + supplier + '\''
|
||||
+ '}';
|
||||
}
|
||||
}
|
@@ -1,264 +0,0 @@
|
||||
package com.iluwatar.datatransferenum;
|
||||
|
||||
/**
|
||||
* {@link ProductDto} is a data transfer object POJO.
|
||||
* Instead of sending individual information to
|
||||
* client We can send related information together in POJO.
|
||||
*
|
||||
* <p>Dto will not have any business logic in it.
|
||||
*/
|
||||
public enum ProductDto {
|
||||
;
|
||||
|
||||
/**
|
||||
* This is Request class which consist of Create or any other request DTO's
|
||||
* you might want to use in your API.
|
||||
*/
|
||||
public enum Request {
|
||||
;
|
||||
|
||||
/**
|
||||
* This is Create dto class for requesting create new product.
|
||||
*/
|
||||
public static final class Create implements Name, Price, Cost, Supplier {
|
||||
private String name;
|
||||
private Double price;
|
||||
private Double cost;
|
||||
private String supplier;
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public Create setName(String name) {
|
||||
this.name = name;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Double getPrice() {
|
||||
return price;
|
||||
}
|
||||
|
||||
public Create setPrice(Double price) {
|
||||
this.price = price;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Double getCost() {
|
||||
return cost;
|
||||
}
|
||||
|
||||
public Create setCost(Double cost) {
|
||||
this.cost = cost;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getSupplier() {
|
||||
return supplier;
|
||||
}
|
||||
|
||||
public Create setSupplier(String supplier) {
|
||||
this.supplier = supplier;
|
||||
return this;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* This is Response class which consist of any response DTO's
|
||||
* you might want to provide to your clients.
|
||||
*/
|
||||
public enum Response {
|
||||
;
|
||||
|
||||
/**
|
||||
* This is Public dto class for API response with the lowest data security.
|
||||
*/
|
||||
public static final class Public implements Id, Name, Price {
|
||||
private Long id;
|
||||
private String name;
|
||||
private Double price;
|
||||
|
||||
@Override
|
||||
public Long getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public Public setId(Long id) {
|
||||
this.id = id;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public Public setName(String name) {
|
||||
this.name = name;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Double getPrice() {
|
||||
return price;
|
||||
}
|
||||
|
||||
public Public setPrice(Double price) {
|
||||
this.price = price;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "Public{"
|
||||
+ "id="
|
||||
+ id
|
||||
+ ", name='"
|
||||
+ name
|
||||
+ '\''
|
||||
+ ", price="
|
||||
+ price
|
||||
+ '}';
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* This is Private dto class for API response with the highest data security.
|
||||
*/
|
||||
public static final class Private implements Id, Name, Price, Cost {
|
||||
private Long id;
|
||||
private String name;
|
||||
private Double price;
|
||||
private Double cost;
|
||||
|
||||
@Override
|
||||
public Long getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public Private setId(Long id) {
|
||||
this.id = id;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public Private setName(String name) {
|
||||
this.name = name;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Double getPrice() {
|
||||
return price;
|
||||
}
|
||||
|
||||
public Private setPrice(Double price) {
|
||||
this.price = price;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Double getCost() {
|
||||
return cost;
|
||||
}
|
||||
|
||||
public Private setCost(Double cost) {
|
||||
this.cost = cost;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "Private{"
|
||||
+
|
||||
"id="
|
||||
+ id
|
||||
+
|
||||
", name='"
|
||||
+ name
|
||||
+ '\''
|
||||
+
|
||||
", price="
|
||||
+ price
|
||||
+
|
||||
", cost="
|
||||
+ cost
|
||||
+
|
||||
'}';
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Use this interface whenever you want to provide the product Id in your DTO.
|
||||
*/
|
||||
private interface Id {
|
||||
/**
|
||||
* Unique identifier of the product.
|
||||
*
|
||||
* @return : id of the product.
|
||||
*/
|
||||
Long getId();
|
||||
}
|
||||
|
||||
/**
|
||||
* Use this interface whenever you want to provide the product Name in your DTO.
|
||||
*/
|
||||
private interface Name {
|
||||
/**
|
||||
* The name of the product.
|
||||
*
|
||||
* @return : name of the product.
|
||||
*/
|
||||
String getName();
|
||||
}
|
||||
|
||||
/**
|
||||
* Use this interface whenever you want to provide the product Price in your DTO.
|
||||
*/
|
||||
private interface Price {
|
||||
/**
|
||||
* The amount we sell a product for.
|
||||
* <b>This data is not confidential</b>
|
||||
*
|
||||
* @return : price of the product.
|
||||
*/
|
||||
Double getPrice();
|
||||
}
|
||||
|
||||
/**
|
||||
* Use this interface whenever you want to provide the product Cost in your DTO.
|
||||
*/
|
||||
private interface Cost {
|
||||
/**
|
||||
* The amount that it costs us to purchase this product
|
||||
* For the amount we sell a product for, see the {@link Price Price} parameter.
|
||||
* <b>This data is confidential</b>
|
||||
*
|
||||
* @return : cost of the product.
|
||||
*/
|
||||
Double getCost();
|
||||
}
|
||||
|
||||
/**
|
||||
* Use this interface whenever you want to provide the product Supplier in your DTO.
|
||||
*/
|
||||
private interface Supplier {
|
||||
/**
|
||||
* The name of supplier of the product or its manufacturer.
|
||||
* <b>This data is highly confidential</b>
|
||||
*
|
||||
* @return : supplier of the product.
|
||||
*/
|
||||
String getSupplier();
|
||||
}
|
||||
}
|
@@ -1,71 +0,0 @@
|
||||
package com.iluwatar.datatransferenum;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
* The resource class which serves product information. This class act as server in the demo. Which
|
||||
* has all product details.
|
||||
*/
|
||||
public class ProductResource {
|
||||
private final List<Product> products;
|
||||
|
||||
/**
|
||||
* Initialise resource with existing products.
|
||||
*
|
||||
* @param products initialize resource with existing products. Act as database.
|
||||
*/
|
||||
public ProductResource(final List<Product> products) {
|
||||
this.products = products;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get all products.
|
||||
*
|
||||
* @return : all products in list but in the scheme of private dto.
|
||||
*/
|
||||
public List<ProductDto.Response.Private> getAllProductsForAdmin() {
|
||||
return products
|
||||
.stream()
|
||||
.map(p -> new ProductDto.Response.Private().setId(p.getId()).setName(p.getName())
|
||||
.setCost(p.getCost())
|
||||
.setPrice(p.getPrice()))
|
||||
.collect(Collectors.toList());
|
||||
}
|
||||
|
||||
/**
|
||||
* Get all products.
|
||||
*
|
||||
* @return : all products in list but in the scheme of public dto.
|
||||
*/
|
||||
public List<ProductDto.Response.Public> getAllProductsForCustomer() {
|
||||
return products
|
||||
.stream()
|
||||
.map(p -> new ProductDto.Response.Public().setId(p.getId()).setName(p.getName())
|
||||
.setPrice(p.getPrice()))
|
||||
.collect(Collectors.toList());
|
||||
}
|
||||
|
||||
/**
|
||||
* Save new product.
|
||||
*
|
||||
* @param createProductDto save new product to list.
|
||||
*/
|
||||
public void save(ProductDto.Request.Create createProductDto) {
|
||||
products.add(new Product()
|
||||
.setId((long) (products.size() + 1))
|
||||
.setName(createProductDto.getName())
|
||||
.setSupplier(createProductDto.getSupplier())
|
||||
.setPrice(createProductDto.getPrice())
|
||||
.setCost(createProductDto.getCost()));
|
||||
}
|
||||
|
||||
/**
|
||||
* List of all products in an entity representation.
|
||||
*
|
||||
* @return : all the products entity that stored in the products list
|
||||
*/
|
||||
public List<Product> getProducts() {
|
||||
return products;
|
||||
}
|
||||
}
|
@@ -1,44 +0,0 @@
|
||||
/*
|
||||
* The MIT License
|
||||
* Copyright © 2014-2019 Ilkka Seppälä
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
* THE SOFTWARE.
|
||||
*/
|
||||
|
||||
package com.iluwatar.datatransferenum;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertDoesNotThrow;
|
||||
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
class AppTest {
|
||||
|
||||
/**
|
||||
* Issue: Add at least one assertion to this test case.
|
||||
* <p>
|
||||
* Solution: Inserted assertion to check whether the execution of the main method in {@link App#main(String[])}
|
||||
* throws an exception.
|
||||
*/
|
||||
|
||||
@Test
|
||||
void shouldExecuteApplicationWithoutException() {
|
||||
assertDoesNotThrow(() -> App.main(new String[] {}));
|
||||
}
|
||||
}
|
@@ -126,16 +126,6 @@ Cons
|
||||
|
||||
* The code becomes more complicated than it should be.
|
||||
|
||||
## Real world examples
|
||||
|
||||
* [java.util.Calendar#getInstance()](https://docs.oracle.com/javase/8/docs/api/java/util/Calendar.html#getInstance--)
|
||||
* [java.util.ResourceBundle#getBundle()](https://docs.oracle.com/javase/8/docs/api/java/util/ResourceBundle.html#getBundle-java.lang.String-)
|
||||
* [java.text.NumberFormat#getInstance()](https://docs.oracle.com/javase/8/docs/api/java/text/NumberFormat.html#getInstance--)
|
||||
* [java.nio.charset.Charset#forName()](https://docs.oracle.com/javase/8/docs/api/java/nio/charset/Charset.html#forName-java.lang.String-)
|
||||
* [java.net.URLStreamHandlerFactory#createURLStreamHandler(String)](https://docs.oracle.com/javase/8/docs/api/java/net/URLStreamHandlerFactory.html) (Returns different singleton objects, depending on a protocol)
|
||||
* [java.util.EnumSet#of()](https://docs.oracle.com/javase/8/docs/api/java/util/EnumSet.html#of(E))
|
||||
* [javax.xml.bind.JAXBContext#createMarshaller()](https://docs.oracle.com/javase/8/docs/api/javax/xml/bind/JAXBContext.html#createMarshaller--) and other similar methods.
|
||||
|
||||
## Related patterns
|
||||
|
||||
* [Factory Method](https://java-design-patterns.com/patterns/factory-method/)
|
||||
|
263
ko/README.md
263
ko/README.md
@@ -1,263 +0,0 @@
|
||||
<!-- the line below needs to be an empty line C: (its because kramdown isnt
|
||||
that smart and dearly wants an empty line before a heading to be able to
|
||||
display it as such, e.g. website) -->
|
||||
|
||||
# 자바로 구현된 디자인 패턴
|
||||
|
||||
[](https://raw.githubusercontent.com/iluwatar/java-design-patterns/master/LICENSE.md)[](https://sonarcloud.io/dashboard?id=iluwatar_java-design-patterns)
|
||||
|
||||
<!-- ALL-CONTRIBUTORS-BADGE:START - Do not remove or modify this section -->
|
||||
|
||||
[](#contributors-)
|
||||
|
||||
<!-- ALL-CONTRIBUTORS-BADGE:END -->
|
||||
|
||||
# 소개
|
||||
|
||||
디자인 패턴은 프로그래머가 응용 프로그램이나 시스템을 디자인 할 때 일반적인 문제를 해결하는 데 사용할 수있는 가장 공식화 된 방법입니다.
|
||||
|
||||
디자인 패턴은 테스트되고 입증 된 개발 패러다임을 제공하여 개발 프로세스 속도를 높일 수 있습니다.
|
||||
|
||||
디자인 패턴을 재사용하면 주요 문제를 유발하는 미묘한 이슈들을 방지하는데 도움이 되며 또한 패턴에 익숙한 코더와 아키텍트의 코드 가독성도 향상됩니다.
|
||||
|
||||
# 시작하기
|
||||
|
||||
이 사이트는 Java 디자인 패턴을 보여줍니다. 이 솔루션은 오픈 소스 커뮤니티의 경험이 많은 프로그래머와 설계자가 개발했습니다. 패턴은 높은 수준의 설명이나 소스 코드를 통해 찾아 볼 수 있습니다. 소스 코드 예제는 잘 설명되어 있으며 특정 패턴을 구현하는 방법을 알려주는 프로그래밍 튜토리얼로 생각할 수 있습니다. 우리는 가장 널리 알려지고 실무에서 입증된 오픈 소스 Java 기술을 사용합니다.
|
||||
|
||||
자료를 살펴보기 전에 다양한 [소프트웨어 설계 원칙](https://java-design-patterns.com/principles/)을 숙지해야합니다.
|
||||
|
||||
모든 디자인은 가능한 한 단순해야합니다. 당신은 KISS, YAGNI로 시작해야하며, 원칙을 작동 할 수 있는 가장 단순한 일을 해야합니다. 복잡성과 패턴은 실용적인 확장성을 위해 필요할 때만 도입되어야합니다.
|
||||
|
||||
이러한 개념에 익숙해지면 다음 접근 방식 중 하나를 이용하여 [사용 가능한 디자인 패턴](https://java-design-patterns.com/patterns/)으로 드릴다운 할 수 있습니다.
|
||||
|
||||
- 이름으로 특정 패턴을 검색합니다. 찾을 수 없습니까? [여기](https://github.com/iluwatar/java-design-patterns/issues)에서 새 패턴을 보고하십시오.
|
||||
- `Performance`, `Gang of Four` 또는 `Data access` 태그 사용.
|
||||
- 패턴 카테고리, `Creational`, `Behavioral` 및 기타 사용
|
||||
|
||||
이 사이트에 제시된 객체 지향 솔루션이 여러분의 아키텍처에서 유용하고 우리가 개발 한 것만큼 재미있게 배우기를 바랍니다.
|
||||
|
||||
# 기여하는 방법
|
||||
|
||||
프로젝트에 기여할 의향이 있다면 [developer wiki](https://github.com/iluwatar/java-design-patterns/wiki)에서 관련 정보를 찾을 수 있습니다. [Gitter chatroom](https://gitter.im/iluwatar/java-design-patterns)에서 귀하를 돕고 질문에 답변 해 드리겠습니다.
|
||||
|
||||
# 특허
|
||||
|
||||
이 프로젝트는 MIT 라이센스 조건에 따라 라이센스가 부여됩니다.
|
||||
|
||||
# 기여자
|
||||
|
||||
<!-- ALL-CONTRIBUTORS-LIST:START - Do not remove or modify this section -->
|
||||
|
||||
<!-- prettier-ignore-start -->
|
||||
|
||||
<!-- markdownlint-disable -->
|
||||
|
||||
<table>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/iluwatar"><img src="https://avatars1.githubusercontent.com/u/582346?v=4" width="100px;" alt=""><br><sub><b>Ilkka Seppälä</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/amit1307"><img src="https://avatars0.githubusercontent.com/u/23420222?v=4" width="100px;" alt=""><br><sub><b>amit1307</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/npathai"><img src="https://avatars2.githubusercontent.com/u/1792515?v=4" width="100px;" alt=""><br><sub><b>Narendra Pathai</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/fluxw42"><img src="https://avatars1.githubusercontent.com/u/1545460?v=4" width="100px;" alt=""><br><sub><b>Jeroen Meulemeester</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="http://www.joemccarthy.co.uk"><img src="https://avatars0.githubusercontent.com/u/4526195?v=4" width="100px;" alt=""><br><sub><b>Joseph McCarthy</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/thomasoss"><img src="https://avatars1.githubusercontent.com/u/22516154?v=4" width="100px;" alt=""><br><sub><b>Thomas</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/anuragagarwal561994"><img src="https://avatars1.githubusercontent.com/u/6075379?v=4" width="100px;" alt=""><br><sub><b>Anurag Agarwal</b></sub></a></td>
|
||||
<td align="center"><a href="https://markusmo3.github.io"><img src="https://avatars1.githubusercontent.com/u/3317416?v=4" width="100px;" alt=""><br><sub><b>Markus Moser</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://twitter.com/i_sabiq"><img src="https://avatars1.githubusercontent.com/u/19510920?v=4" width="100px;" alt=""><br><sub><b>Sabiq Ihab</b></sub></a></td>
|
||||
<td align="center"><a href="http://inbravo.github.io"><img src="https://avatars3.githubusercontent.com/u/5253764?v=4" width="100px;" alt=""><br><sub><b>Amit Dixit</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/piyushchaudhari04"><img src="https://avatars3.githubusercontent.com/u/10268029?v=4" width="100px;" alt=""><br><sub><b>Piyush Kailash Chaudhari</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/joshzambales"><img src="https://avatars1.githubusercontent.com/u/8704552?v=4" width="100px;" alt=""><br><sub><b>joshzambales</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/Crossy147"><img src="https://avatars2.githubusercontent.com/u/7272996?v=4" width="100px;" alt=""><br><sub><b>Kamil Pietruszka</b></sub></a></td>
|
||||
<td align="center"><a href="http://cs.joensuu.fi/~zkhayda"><img src="https://avatars2.githubusercontent.com/u/660742?v=4" width="100px;" alt=""><br><sub><b>Zafar Khaydarov</b></sub></a></td>
|
||||
<td align="center"><a href="https://kemitix.github.io/"><img src="https://avatars1.githubusercontent.com/u/1147749?v=4" width="100px;" alt=""><br><sub><b>Paul Campbell</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/Argyro-Sioziou"><img src="https://avatars0.githubusercontent.com/u/22822639?v=4" width="100px;" alt=""><br><sub><b>Argyro Sioziou</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/TylerMcConville"><img src="https://avatars0.githubusercontent.com/u/4946449?v=4" width="100px;" alt=""><br><sub><b>TylerMcConville</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/saksham93"><img src="https://avatars1.githubusercontent.com/u/37399540?v=4" width="100px;" alt=""><br><sub><b>saksham93</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/nikhilbarar"><img src="https://avatars2.githubusercontent.com/u/37332144?v=4" width="100px;" alt=""><br><sub><b>nikhilbarar</b></sub></a></td>
|
||||
<td align="center"><a href="http://colinbut.com"><img src="https://avatars2.githubusercontent.com/u/10725674?v=4" width="100px;" alt=""><br><sub><b>Colin But</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/ruslanpa"><img src="https://avatars2.githubusercontent.com/u/1503411?v=4" width="100px;" alt=""><br><sub><b>Ruslan</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/JuhoKang"><img src="https://avatars1.githubusercontent.com/u/4745294?v=4" width="100px;" alt=""><br><sub><b>Juho Kang</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/dheeraj-mummareddy"><img src="https://avatars2.githubusercontent.com/u/7002230?v=4" width="100px;" alt=""><br><sub><b>Dheeraj Mummareddy</b></sub></a></td>
|
||||
<td align="center"><a href="https://www.bernardosulzbach.com"><img src="https://avatars0.githubusercontent.com/u/8271090?v=4" width="100px;" alt=""><br><sub><b>Bernardo Sulzbach</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/4lexis"><img src="https://avatars0.githubusercontent.com/u/19871727?v=4" width="100px;" alt=""><br><sub><b>Aleksandar Dudukovic</b></sub></a></td>
|
||||
<td align="center"><a href="https://www.yusufaytas.com"><img src="https://avatars2.githubusercontent.com/u/1049483?v=4" width="100px;" alt=""><br><sub><b>Yusuf Aytaş</b></sub></a></td>
|
||||
<td align="center"><a href="http://futurehomes.hu"><img src="https://avatars2.githubusercontent.com/u/1001491?v=4" width="100px;" alt=""><br><sub><b>Mihály Kuprivecz</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/kapinuss"><img src="https://avatars0.githubusercontent.com/u/17639945?v=4" width="100px;" alt=""><br><sub><b>Stanislav Kapinus</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/gvsharma"><img src="https://avatars1.githubusercontent.com/u/6648152?v=4" width="100px;" alt=""><br><sub><b>GVSharma</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/SrdjanPaunovic"><img src="https://avatars1.githubusercontent.com/u/22815104?v=4" width="100px;" alt=""><br><sub><b>Srđan Paunović</b></sub></a></td>
|
||||
<td align="center"><a href="https://sideris.xyz/"><img src="https://avatars3.githubusercontent.com/u/5484694?v=4" width="100px;" alt=""><br><sub><b>Petros G. Sideris</b></sub></a></td>
|
||||
<td align="center"><a href="https://www.linkedin.com/in/pramodgupta3/"><img src="https://avatars1.githubusercontent.com/u/2184241?v=4" width="100px;" alt=""><br><sub><b>Pramod Gupta</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://amarnath510.github.io/portfolio"><img src="https://avatars0.githubusercontent.com/u/4599623?v=4" width="100px;" alt=""><br><sub><b>Amarnath Chandana</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/Anurag870"><img src="https://avatars1.githubusercontent.com/u/6295975?v=4" width="100px;" alt=""><br><sub><b>Anurag870</b></sub></a></td>
|
||||
<td align="center"><a href="http://theerroris.me"><img src="https://avatars0.githubusercontent.com/u/1685953?v=4" width="100px;" alt=""><br><sub><b>Wes Gilleland</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/Harshrajsinh"><img src="https://avatars2.githubusercontent.com/u/22811531?v=4" width="100px;" alt=""><br><sub><b>Harshraj Thakor</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/MaVdbussche"><img src="https://avatars1.githubusercontent.com/u/26136934?v=4" width="100px;" alt=""><br><sub><b>Martin Vandenbussche</b></sub></a></td>
|
||||
<td align="center"><a href="https://alexsomai.com"><img src="https://avatars1.githubusercontent.com/u/5720977?v=4" width="100px;" alt=""><br><sub><b>Alexandru Somai</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/amogozov"><img src="https://avatars3.githubusercontent.com/u/7372215?v=4" width="100px;" alt=""><br><sub><b>Artur Mogozov</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/anthonycampbell"><img src="https://avatars3.githubusercontent.com/u/10249255?v=4" width="100px;" alt=""><br><sub><b>anthony</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="http://ccygnus.com/"><img src="https://avatars1.githubusercontent.com/u/9342724?v=4" width="100px;" alt=""><br><sub><b>Christian Cygnus</b></sub></a></td>
|
||||
<td align="center"><a href="https://about.me/dzmitryh"><img src="https://avatars2.githubusercontent.com/u/5390492?v=4" width="100px;" alt=""><br><sub><b>Dima Gubin</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/jjjimenez100"><img src="https://avatars3.githubusercontent.com/u/22243493?v=4" width="100px;" alt=""><br><sub><b>Joshua Jimenez</b></sub></a></td>
|
||||
<td align="center"><a href="http://about.me/kaiwinter"><img src="https://avatars0.githubusercontent.com/u/110982?v=4" width="100px;" alt=""><br><sub><b>Kai Winter</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/lbroman"><img src="https://avatars1.githubusercontent.com/u/86007?v=4" width="100px;" alt=""><br><sub><b>lbroman</b></sub></a></td>
|
||||
<td align="center"><a href="https://przemeknowak.com"><img src="https://avatars1.githubusercontent.com/u/3254609?v=4" width="100px;" alt=""><br><sub><b>Przemek</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/prafful1"><img src="https://avatars0.githubusercontent.com/u/14350274?v=4" width="100px;" alt=""><br><sub><b>Prafful Agarwal</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/sankypanhale"><img src="https://avatars1.githubusercontent.com/u/6478783?v=4" width="100px;" alt=""><br><sub><b>Sanket Panhale</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/staillebois"><img src="https://avatars0.githubusercontent.com/u/23701200?v=4" width="100px;" alt=""><br><sub><b>staillebois</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/valdar-hu"><img src="https://avatars3.githubusercontent.com/u/17962817?v=4" width="100px;" alt=""><br><sub><b>Krisztián Nagy</b></sub></a></td>
|
||||
<td align="center"><a href="https://www.vanogrid.com"><img src="https://avatars0.githubusercontent.com/u/4307918?v=4" width="100px;" alt=""><br><sub><b>Alexander Ivanov</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/yosfik"><img src="https://avatars3.githubusercontent.com/u/4850270?v=4" width="100px;" alt=""><br><sub><b>Yosfik Alqadri</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/7agustibm"><img src="https://avatars0.githubusercontent.com/u/8149332?v=4" width="100px;" alt=""><br><sub><b>Agustí Becerra Milà</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/Juaanma"><img src="https://avatars3.githubusercontent.com/u/7390500?v=4" width="100px;" alt=""><br><sub><b>Juan Manuel Suárez</b></sub></a></td>
|
||||
<td align="center"><a href="http://www.devsedge.net/"><img src="https://avatars0.githubusercontent.com/u/9956006?v=4" width="100px;" alt=""><br><sub><b>Luigi Cortese</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/Rzeposlaw"><img src="https://avatars2.githubusercontent.com/u/18425745?v=4" width="100px;" alt=""><br><sub><b>Katarzyna Rzepecka</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="http://adamski.pro"><img src="https://avatars1.githubusercontent.com/u/6537430?v=4" width="100px;" alt=""><br><sub><b>adamski.pro</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/baislsl"><img src="https://avatars0.githubusercontent.com/u/17060584?v=4" width="100px;" alt=""><br><sub><b>Shengli Bai</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/besok"><img src="https://avatars2.githubusercontent.com/u/29834592?v=4" width="100px;" alt=""><br><sub><b>Boris</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/dmitraver"><img src="https://avatars3.githubusercontent.com/u/1798156?v=4" width="100px;" alt=""><br><sub><b>Dmitry Avershin</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/fanofxiaofeng"><img src="https://avatars0.githubusercontent.com/u/3983683?v=4" width="100px;" alt=""><br><sub><b>靳阳</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/hoangnam2261"><img src="https://avatars2.githubusercontent.com/u/31692990?v=4" width="100px;" alt=""><br><sub><b>hoangnam2261</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/jarpit96"><img src="https://avatars2.githubusercontent.com/u/10098713?v=4" width="100px;" alt=""><br><sub><b>Arpit Jain</b></sub></a></td>
|
||||
<td align="center"><a href="http://joningi.net"><img src="https://avatars2.githubusercontent.com/u/6115148?v=4" width="100px;" alt=""><br><sub><b>Jón Ingi Sveinbjörnsson</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/kirill-vlasov"><img src="https://avatars3.githubusercontent.com/u/16112495?v=4" width="100px;" alt=""><br><sub><b>Kirill Vlasov</b></sub></a></td>
|
||||
<td align="center"><a href="http://mitchell-irvin.com"><img src="https://avatars0.githubusercontent.com/u/16233245?v=4" width="100px;" alt=""><br><sub><b>Mitchell Irvin</b></sub></a></td>
|
||||
<td align="center"><a href="https://ranjeet-floyd.github.io"><img src="https://avatars0.githubusercontent.com/u/1992972?v=4" width="100px;" alt=""><br><sub><b>Ranjeet</b></sub></a></td>
|
||||
<td align="center"><a href="https://alwayswithme.github.io"><img src="https://avatars3.githubusercontent.com/u/3234786?v=4" width="100px;" alt=""><br><sub><b>PhoenixYip</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/MSaifAsif"><img src="https://avatars1.githubusercontent.com/u/6280554?v=4" width="100px;" alt=""><br><sub><b>M Saif Asif</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/kanwarpreet25"><img src="https://avatars0.githubusercontent.com/u/39183641?v=4" width="100px;" alt=""><br><sub><b>kanwarpreet25</b></sub></a></td>
|
||||
<td align="center"><a href="http://leonmak.me"><img src="https://avatars3.githubusercontent.com/u/13071508?v=4" width="100px;" alt=""><br><sub><b>Leon Mak</b></sub></a></td>
|
||||
<td align="center"><a href="http://www.wramdemark.se"><img src="https://avatars2.githubusercontent.com/u/7052193?v=4" width="100px;" alt=""><br><sub><b>Per Wramdemark</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/waisuan"><img src="https://avatars2.githubusercontent.com/u/10975700?v=4" width="100px;" alt=""><br><sub><b>Evan Sia Wai Suan</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/AnaghaSasikumar"><img src="https://avatars2.githubusercontent.com/u/42939261?v=4" width="100px;" alt=""><br><sub><b>AnaghaSasikumar</b></sub></a></td>
|
||||
<td align="center"><a href="https://christofferh.com"><img src="https://avatars1.githubusercontent.com/u/767643?v=4" width="100px;" alt=""><br><sub><b>Christoffer Hamberg</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/dgruntz"><img src="https://avatars0.githubusercontent.com/u/1516800?v=4" width="100px;" alt=""><br><sub><b>Dominik Gruntz</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://bitbucket.org/hannespernpeintner/"><img src="https://avatars3.githubusercontent.com/u/1679437?v=4" width="100px;" alt=""><br><sub><b>Hannes</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/leogtzr"><img src="https://avatars0.githubusercontent.com/u/1211969?v=4" width="100px;" alt=""><br><sub><b>Leo Gutiérrez Ramírez</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/npczwh"><img src="https://avatars0.githubusercontent.com/u/14066422?v=4" width="100px;" alt=""><br><sub><b>Zhang WH</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/oconnelc"><img src="https://avatars0.githubusercontent.com/u/1112973?v=4" width="100px;" alt=""><br><sub><b>Christopher O'Connell</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/giorgosmav21"><img src="https://avatars2.githubusercontent.com/u/22855493?v=4" width="100px;" alt=""><br><sub><b>George Mavroeidis</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/hbothra15"><img src="https://avatars1.githubusercontent.com/u/7418012?v=4" width="100px;" alt=""><br><sub><b>Hemant Bothra</b></sub></a></td>
|
||||
<td align="center"><a href="https://www.kevinpeters.net/about/"><img src="https://avatars1.githubusercontent.com/u/12736734?v=4" width="100px;" alt=""><br><sub><b>Kevin Peters</b></sub></a></td>
|
||||
<td align="center"><a href="https://llorllale.github.io/"><img src="https://avatars1.githubusercontent.com/u/2019896?v=4" width="100px;" alt=""><br><sub><b>George Aristy</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/mookkiah"><img src="https://avatars1.githubusercontent.com/u/8975264?v=4" width="100px;" alt=""><br><sub><b>Mahendran Mookkiah</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/Azureyjt"><img src="https://avatars2.githubusercontent.com/u/18476317?v=4" width="100px;" alt=""><br><sub><b>Azureyjt</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/vehpsr"><img src="https://avatars2.githubusercontent.com/u/3133265?v=4" width="100px;" alt=""><br><sub><b>gans</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/ThatGuyWithTheHat"><img src="https://avatars0.githubusercontent.com/u/24470582?v=4" width="100px;" alt=""><br><sub><b>Matt</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://www.linkedin.com/in/gopinathlangote/"><img src="https://avatars2.githubusercontent.com/u/10210778?v=4" width="100px;" alt=""><br><sub><b>Gopinath Langote</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/hoswey"><img src="https://avatars3.githubusercontent.com/u/3689445?v=4" width="100px;" alt=""><br><sub><b>Hoswey</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/amit2103"><img src="https://avatars3.githubusercontent.com/u/7566692?v=4" width="100px;" alt=""><br><sub><b>Amit Pandey</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/gwildor28"><img src="https://avatars0.githubusercontent.com/u/16000365?v=4" width="100px;" alt=""><br><sub><b>gwildor28</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://t.me/paul_docker"><img src="https://avatars1.githubusercontent.com/u/2404785?v=4" width="100px;" alt=""><br><sub><b>田浩</b></sub></a></td>
|
||||
<td align="center"><a href="https://twitter.com/StPitsios"><img src="https://avatars1.githubusercontent.com/u/6773603?v=4" width="100px;" alt=""><br><sub><b>Stamatis Pitsios</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/qza"><img src="https://avatars3.githubusercontent.com/u/233149?v=4" width="100px;" alt=""><br><sub><b>qza</b></sub></a></td>
|
||||
<td align="center"><a href="http://tschis.github.io"><img src="https://avatars1.githubusercontent.com/u/20662669?v=4" width="100px;" alt=""><br><sub><b>Rodolfo Forte</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/ankurkaushal"><img src="https://avatars2.githubusercontent.com/u/2236616?v=4" width="100px;" alt=""><br><sub><b>Ankur Kaushal</b></sub></a></td>
|
||||
<td align="center"><a href="https://www.linkedin.com/in/ovidijus-okinskas/"><img src="https://avatars0.githubusercontent.com/u/20372387?v=4" width="100px;" alt=""><br><sub><b>Ovidijus Okinskas</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/robertt240"><img src="https://avatars1.githubusercontent.com/u/9137432?v=4" width="100px;" alt=""><br><sub><b>Robert Kasperczyk</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/trautonen"><img src="https://avatars3.githubusercontent.com/u/1641063?v=4" width="100px;" alt=""><br><sub><b>Tapio Rautonen</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="http://vk.com/yuri.orlov"><img src="https://avatars0.githubusercontent.com/u/1595733?v=4" width="100px;" alt=""><br><sub><b>Yuri Orlov</b></sub></a></td>
|
||||
<td align="center"><a href="https://www.linkedin.com/in/varunu28/"><img src="https://avatars0.githubusercontent.com/u/7676016?v=4" width="100px;" alt=""><br><sub><b>Varun Upadhyay</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/PalAditya"><img src="https://avatars2.githubusercontent.com/u/25523604?v=4" width="100px;" alt=""><br><sub><b>Aditya Pal</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/grzesiekkedzior"><img src="https://avatars3.githubusercontent.com/u/23739158?v=4" width="100px;" alt=""><br><sub><b>grzesiekkedzior</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/sivasubramanim"><img src="https://avatars2.githubusercontent.com/u/51107434?v=4" width="100px;" alt=""><br><sub><b>Sivasubramani M</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/d4gg4d"><img src="https://avatars2.githubusercontent.com/u/99457?v=4" width="100px;" alt=""><br><sub><b>Sami Airaksinen</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/vertti"><img src="https://avatars0.githubusercontent.com/u/557751?v=4" width="100px;" alt=""><br><sub><b>Janne Sinivirta</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/Bobo1239"><img src="https://avatars1.githubusercontent.com/u/2302947?v=4" width="100px;" alt=""><br><sub><b>Boris-Chengbiao Zhou</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://jahhein.github.io"><img src="https://avatars2.githubusercontent.com/u/10779515?v=4" width="100px;" alt=""><br><sub><b>Jacob Hein</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/iamrichardjones"><img src="https://avatars3.githubusercontent.com/u/14842151?v=4" width="100px;" alt=""><br><sub><b>Richard Jones</b></sub></a></td>
|
||||
<td align="center"><a href="https://rachelcarmena.github.io"><img src="https://avatars0.githubusercontent.com/u/22792183?v=4" width="100px;" alt=""><br><sub><b>Rachel M. Carmena</b></sub></a></td>
|
||||
<td align="center"><a href="https://zd-zero.github.io"><img src="https://avatars0.githubusercontent.com/u/21978370?v=4" width="100px;" alt=""><br><sub><b>Zaerald Denze Lungos</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://webpro.nl"><img src="https://avatars1.githubusercontent.com/u/456426?v=4" width="100px;" alt=""><br><sub><b>Lars Kappert</b></sub></a></td>
|
||||
<td align="center"><a href="https://xiaod.info"><img src="https://avatars2.githubusercontent.com/u/21277644?v=4" width="100px;" alt=""><br><sub><b>Mike Liu</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/charlesfinley"><img src="https://avatars1.githubusercontent.com/u/6307904?v=4" width="100px;" alt=""><br><sub><b>Matt Dolan</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/MananS77"><img src="https://avatars3.githubusercontent.com/u/21033516?v=4" width="100px;" alt=""><br><sub><b>Manan</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/nishant"><img src="https://avatars2.githubusercontent.com/u/15331971?v=4" width="100px;" alt=""><br><sub><b>Nishant Arora</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/raja-peeyush-kumar-singh"><img src="https://avatars0.githubusercontent.com/u/5496024?v=4" width="100px;" alt=""><br><sub><b>Peeyush</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/ravening"><img src="https://avatars1.githubusercontent.com/u/10645273?v=4" width="100px;" alt=""><br><sub><b>Rakesh</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/vINCENT8888801"><img src="https://avatars0.githubusercontent.com/u/8037883?v=4" width="100px;" alt=""><br><sub><b>Wei Seng</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://www.linkedin.com/in/ashish-trivedi-218379135/"><img src="https://avatars3.githubusercontent.com/u/23194128?v=4" width="100px;" alt=""><br><sub><b>Ashish Trivedi</b></sub></a></td>
|
||||
<td align="center"><a href="https://rayyounghong.com"><img src="https://avatars1.githubusercontent.com/u/41055099?v=4" width="100px;" alt=""><br><sub><b>洪月阳</b></sub></a></td>
|
||||
<td align="center"><a href="https://xdvrx1.github.io/"><img src="https://avatars0.githubusercontent.com/u/47092464?v=4" width="100px;" alt=""><br><sub><b>xdvrx1</b></sub></a></td>
|
||||
<td align="center"><a href="http://subho.xyz"><img src="https://avatars0.githubusercontent.com/u/13291222?v=4" width="100px;" alt=""><br><sub><b>Subhrodip Mohanta</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/nahteb"><img src="https://avatars3.githubusercontent.com/u/13121570?v=4" width="100px;" alt=""><br><sub><b>Bethan Palmer</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/ToxicDreamz"><img src="https://avatars0.githubusercontent.com/u/45225562?v=4" width="100px;" alt=""><br><sub><b>Toxic Dreamz</b></sub></a></td>
|
||||
<td align="center"><a href="http://www.edycutjong.com"><img src="https://avatars1.githubusercontent.com/u/1098102?v=4" width="100px;" alt=""><br><sub><b>Edy Cu Tjong</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/mkrzywanski"><img src="https://avatars0.githubusercontent.com/u/15279585?v=4" width="100px;" alt=""><br><sub><b>Michał Krzywański</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://www.stefan-birkner.de"><img src="https://avatars1.githubusercontent.com/u/711349?v=4" width="100px;" alt=""><br><sub><b>Stefan Birkner</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/fedorskvorcov"><img src="https://avatars3.githubusercontent.com/u/43882212?v=4" width="100px;" alt=""><br><sub><b>Fedor Skvorcov</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/samilAyoub"><img src="https://avatars0.githubusercontent.com/u/61546990?v=4" width="100px;" alt=""><br><sub><b>samilAyoub</b></sub></a></td>
|
||||
<td align="center"><a href="https://github.com/vdlald"><img src="https://avatars0.githubusercontent.com/u/29997701?v=4" width="100px;" alt=""><br><sub><b>Vladislav Golubinov</b></sub></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"><a href="https://github.com/swarajsaaj"><img src="https://avatars2.githubusercontent.com/u/6285049?v=4" width="100px;" alt=""><br><sub><b>Swaraj</b></sub></a></td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
<!-- markdownlint-enable -->
|
||||
|
||||
<!-- prettier-ignore-end -->
|
||||
|
||||
<!-- ALL-CONTRIBUTORS-LIST:END -->
|
@@ -1,134 +0,0 @@
|
||||
---
|
||||
layout: pattern
|
||||
title: Adapter
|
||||
folder: adapter
|
||||
permalink: "/patterns/adapter/"
|
||||
categories: Structural
|
||||
tags:
|
||||
- Gang of Four
|
||||
---
|
||||
|
||||
## 또한 ~으로 알려진
|
||||
|
||||
Wrapper
|
||||
|
||||
## 의도
|
||||
|
||||
클래스의 인터페이스를 클라이언트가 기대하는 다른 인터페이스로 변환합니다. adapter를 사용하면 호환되지 않는 인터페이스로 인해 같이 쓸 수 없는 클래스를 함께 작동 할 수 있습니다.
|
||||
|
||||
## 설명
|
||||
|
||||
예시
|
||||
|
||||
> 메모리 카드에 몇 장의 사진이 있고 컴퓨터로 전송해야한다고 생각하십시오. 이들을 전송하려면 컴퓨터에 메모리 카드를 연결할 수 있도록 컴퓨터 포트와 호환되는 어댑터가 필요합니다. 이 경우 카드 리더는 어댑터입니다. 또 다른 예는 유명한 전원 어댑터입니다. 세 갈래 플러그는 두 갈래 콘센트에 연결할 수 없습니다. 두 갈래 콘센트와 호환되는 전원 어댑터를 사용해야합니다. 또 다른 예는 한 사람이 말한 단어를 다른 사람에게 번역하는 번역가입니다.
|
||||
|
||||
평범하게 말하자면
|
||||
|
||||
> adapter 패턴을 사용하면 호환되지 않는 개체를 adapter에 연결하여 다른 클래스와 호환되도록 할 수 있습니다.
|
||||
|
||||
Wikipedia 말에 의하면
|
||||
|
||||
> 소프트웨어 엔지니어링에서 adapter 패턴은 기존 클래스의 인터페이스를 다른 인터페이스로 사용할 수 있도록 하는 소프트웨어 디자인 패턴입니다. 소스 코드를 수정하지 않고 기존 클래스가 다른 클래스와 함께 작동하도록 만드는 데 자주 사용됩니다.
|
||||
|
||||
**프로그램 코드 예제**
|
||||
|
||||
조정 보트만 사용할 수 있고 전혀 항해할 수 없는 선장을 생각해보십시오.
|
||||
|
||||
먼저 `RowingBoat` 및 `FishingBoat` 인터페이스가 있습니다.
|
||||
|
||||
```java
|
||||
public interface RowingBoat {
|
||||
void row();
|
||||
}
|
||||
|
||||
public class FishingBoat {
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(FishingBoat.class);
|
||||
public void sail() {
|
||||
LOGGER.info("The fishing boat is sailing");
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
그리고 선장은 `RowingBoat` 인터페이스를 이동할 수 있게 구현했습니다.
|
||||
|
||||
```java
|
||||
public class Captain {
|
||||
|
||||
private final RowingBoat rowingBoat;
|
||||
// default constructor and setter for rowingBoat
|
||||
public Captain(RowingBoat rowingBoat) {
|
||||
this.rowingBoat = rowingBoat;
|
||||
}
|
||||
|
||||
public void row() {
|
||||
rowingBoat.row();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
이제 해적이오고 있고 우리 선장이 탈출해야하는데 어선만 있습니다. 선장이 조정 보트 기술로 어선을 조작 할 수있는 adapter를 만들어야합니다.
|
||||
|
||||
```java
|
||||
public class FishingBoatAdapter implements RowingBoat {
|
||||
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(FishingBoatAdapter.class);
|
||||
|
||||
private final FishingBoat boat;
|
||||
|
||||
public FishingBoatAdapter() {
|
||||
boat = new FishingBoat();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void row() {
|
||||
boat.sail();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
이제 `Captain` 은 `FishingBoat` 를 사용하여 해적을 탈출 할 수 있습니다.
|
||||
|
||||
```java
|
||||
var captain = new Captain(new FishingBoatAdapter());
|
||||
captain.row();
|
||||
```
|
||||
|
||||
## 클레스 다이어그램
|
||||
|
||||

|
||||
|
||||
## 적용 가능성
|
||||
|
||||
다음과 같은 경우 adapter 패턴을 사용합니다.
|
||||
|
||||
- 기존 클래스를 사용 하려는데 해당 인터페이스가 필요한 클래스와 일치하지 않습니다.
|
||||
- 관련이 없거나 예상치 못한 클래스, 즉 호환되는 인터페이스가 반드시 필요하지 않은 클래스와 협력하는 재사용 가능한 클래스를 만들고 싶습니다.
|
||||
- 기존의 여러 하위 클래스를 사용해야하지만 모든 하위 클래스를 하위 클래스로 지정하여 인터페이스를 조정하는 것은 비현실적입니다. 개체 adapter는 부모 클래스의 인터페이스를 조정할 수 있습니다.
|
||||
- 타사 라이브러리를 사용하는 대부분의 응용 프로그램은 adapter를 응용 프로그램과 타사 라이브러리 사이의 중간 계층으로 사용하여 라이브러리에서 응용 프로그램을 분리합니다. 다른 라이브러리를 사용해야하는 경우 애플리케이션 코드를 변경할 필요없이 새 라이브러리 용 adapter만 필요합니다.
|
||||
|
||||
## 결과 :
|
||||
|
||||
클래스 및 개체 adapter에는 서로 다른 장단점이 있습니다. <br>클래스 adapter
|
||||
|
||||
- 구체적인 Adaptee 클래스를 커밋하여 Adaptee를 Target에 적용합니다. 결과적으로 클래스와 모든 하위 클래스를 조정하려는 경우 클래스 adapter가 작동하지 않습니다.
|
||||
- adapter는 Adaptee의 하위 클래스이기 때문에 Adaptee의 일부 동작을 오버라이드합니다.
|
||||
- 하나의 객체만 생성하고 adaptee를 얻기위해 위해 추가 포인터 간접 지정이 필요하지 않습니다.
|
||||
|
||||
개체 adapter
|
||||
|
||||
- 하나의 adapter가 많은 Adaptees, 즉 Adaptee 자체와 모든 하위 클래스 (있는 경우)와 함께 작동하도록합시다. adapter는 한 번에 모든 어댑터에 기능을 추가 할 수도 있습니다.
|
||||
- Adaptee 동작을 오버라이드하기가 더 어렵습니다. Adaptee를 서브 클래싱하고 어댑터가 Adaptee 자체가 아닌 서브 클래스를 참조하도록 해야합니다.
|
||||
|
||||
## 실제 사례
|
||||
|
||||
- [java.util.Arrays#asList()](http://docs.oracle.com/javase/8/docs/api/java/util/Arrays.html#asList%28T...%29)
|
||||
- [java.util.Collections#list()](https://docs.oracle.com/javase/8/docs/api/java/util/Collections.html#list-java.util.Enumeration-)
|
||||
- [java.util.Collections#enumeration()](https://docs.oracle.com/javase/8/docs/api/java/util/Collections.html#enumeration-java.util.Collection-)
|
||||
- [javax.xml.bind.annotation.adapters.XMLAdapter](http://docs.oracle.com/javase/8/docs/api/javax/xml/bind/annotation/adapters/XmlAdapter.html#marshal-BoundType-)
|
||||
|
||||
## 크레딧
|
||||
|
||||
- [Design Patterns: Elements of Reusable Object-Oriented Software](https://www.amazon.com/gp/product/0201633612/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0201633612&linkCode=as2&tag=javadesignpat-20&linkId=675d49790ce11db99d90bde47f1aeb59)
|
||||
- [J2EE Design Patterns](https://www.amazon.com/gp/product/0596004273/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596004273&linkCode=as2&tag=javadesignpat-20&linkId=48d37c67fb3d845b802fa9b619ad8f31)
|
||||
- [Head First Design Patterns: A Brain-Friendly Guide](https://www.amazon.com/gp/product/0596007124/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596007124&linkCode=as2&tag=javadesignpat-20&linkId=6b8b6eea86021af6c8e3cd3fc382cb5b)
|
||||
- [Refactoring to Patterns](https://www.amazon.com/gp/product/0321213351/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0321213351&linkCode=as2&tag=javadesignpat-20&linkId=2a76fcb387234bc71b1c61150b3cc3a7)
|
@@ -1,128 +0,0 @@
|
||||
---
|
||||
layout: pattern
|
||||
title: Factory
|
||||
folder: factory
|
||||
permalink: "/patterns/factory/"
|
||||
categories: Creational
|
||||
tags:
|
||||
- Gang of Four
|
||||
---
|
||||
|
||||
## 또한 ~으로 알려진
|
||||
|
||||
- Simple Factory
|
||||
- Static Factory Method
|
||||
|
||||
## 의도
|
||||
|
||||
구현 논리를 숨기고 클라이언트 코드가 새 객체를 초기화하는 대신 사용에 집중하도록하기 위해 factory라는 클래스에 캡슐화 된 정적 메서드를 제공합니다.
|
||||
|
||||
## 설명
|
||||
|
||||
예시
|
||||
|
||||
> SQLServer에 연결된 웹 응용 프로그램이 있지만 이제 Oracle로 전환하려고 합니다. 기존 소스 코드를 수정하지 않고 이를 수행하려면 주어진 데이터베이스에 대한 연결을 생성하기 위해 정적 메서드를 호출 할 수 있는 Simple Factory 패턴을 구현해야합니다.
|
||||
|
||||
Wikipedia 말에 의하면
|
||||
|
||||
> factory는 다른 객체를 생성하기위한 객체입니다. 공식적으로 factory는 다양한 프로토 타입 또는 클래스의 객체를 반환하는 함수 또는 메서드입니다.
|
||||
|
||||
**프로그램 코드 예제**
|
||||
|
||||
우리는 인터페이스 `Car` 와 두 가지 구현 `Ford` 와 `Ferrari`을 가지고 있습니다.
|
||||
|
||||
```java
|
||||
public interface Car {
|
||||
String getDescription();
|
||||
}
|
||||
|
||||
public class Ford implements Car {
|
||||
|
||||
static final String DESCRIPTION = "This is Ford.";
|
||||
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return DESCRIPTION;
|
||||
}
|
||||
}
|
||||
|
||||
public class Ferrari implements Car {
|
||||
|
||||
static final String DESCRIPTION = "This is Ferrari.";
|
||||
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return DESCRIPTION;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
열거형은 우리가 지원하는 자동차 유형을 나타냅니다 ( `Ford` 및 `Ferrari` ).
|
||||
|
||||
```java
|
||||
public enum CarType {
|
||||
|
||||
FORD(Ford::new),
|
||||
FERRARI(Ferrari::new);
|
||||
|
||||
private final Supplier<Car> constructor;
|
||||
|
||||
CarType(Supplier<Car> constructor) {
|
||||
this.constructor = constructor;
|
||||
}
|
||||
|
||||
public Supplier<Car> getConstructor() {
|
||||
return this.constructor;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
그런 다음 factory 클래스 `CarsFactory` 캡슐화 된 자동차 객체를 만드는 정적 메서드 `getCar` 가 있습니다.
|
||||
|
||||
```java
|
||||
public class CarsFactory {
|
||||
|
||||
public static Car getCar(CarType type) {
|
||||
return type.getConstructor().get();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
이제 클라이언트 코드에서 factory 클래스를 사용하여 다양한 유형의 자동차를 만들 수 있습니다.
|
||||
|
||||
```java
|
||||
var car1 = CarsFactory.getCar(CarType.FORD);
|
||||
var car2 = CarsFactory.getCar(CarType.FERRARI);
|
||||
LOGGER.info(car1.getDescription());
|
||||
LOGGER.info(car2.getDescription());;
|
||||
```
|
||||
|
||||
프로그램 출력 :
|
||||
|
||||
```java
|
||||
This is Ford.
|
||||
This Ferrari.
|
||||
```
|
||||
|
||||
## 클래스 다이어그램
|
||||
|
||||

|
||||
|
||||
## 적용 가능성
|
||||
|
||||
객체 생성 및 관리 방법이 아닌 객체 생성에만 관심이있을 때 Simple Factory 패턴을 사용합니다.
|
||||
|
||||
장점
|
||||
|
||||
- 모든 객체 생성을 한곳에 유지하고 코드베이스에 '새'키 값이 확산되는 것을 방지합니다.
|
||||
- 느슨하게 결합 된 코드를 작성할 수 있습니다. 주요 장점 중 일부는 더 나은 테스트 가능성, 이해하기 쉬운 코드, 교체 가능한 구성 요소, 확장성 및 격리된 기능을 포함합니다.
|
||||
|
||||
단점
|
||||
|
||||
- 코드는 생각보다 복잡해집니다.
|
||||
|
||||
## 관련 패턴
|
||||
|
||||
- [Factory Method](https://java-design-patterns.com/patterns/factory-method/)
|
||||
- [Factory Kit](https://java-design-patterns.com/patterns/factory-kit/)
|
||||
- [Abstract Factory](https://java-design-patterns.com/patterns/abstract-factory/)
|
@@ -1,165 +0,0 @@
|
||||
---
|
||||
layout: pattern
|
||||
title: Observer
|
||||
folder: observer
|
||||
permalink: "/patterns/observer/"
|
||||
categories: Behavioral
|
||||
tags:
|
||||
- Gang Of Four
|
||||
- Reactive
|
||||
---
|
||||
|
||||
## 또한 ~으로 알려진
|
||||
|
||||
Dependents, Publish-Subscribe
|
||||
|
||||
## 의도
|
||||
|
||||
하나의 개체가 상태를 변경하면 모든 종속 항목에 알림이 전송되고 자동으로 업데이트 되도록 개체간의 일대 다 종속성을 정의합니다.
|
||||
|
||||
## 설명
|
||||
|
||||
예시
|
||||
|
||||
> 멀리 떨어진 땅에는 호빗과 오크 종족이 살고 있습니다. 둘 다 대부분 야외에 있으므로 날씨 변화를 면밀히 따릅니다. 끊임없이 날씨를 관찰하고 있다고 말할 수 있습니다.
|
||||
|
||||
평범하게 말하자면
|
||||
|
||||
> observer로 등록하여 개체의 상태 변경을 수신합니다.
|
||||
|
||||
Wikipedia 말에 의하면
|
||||
|
||||
> observer 패턴은 주제라고하는 객체가 observer라고 하는 종속 항목 목록을 유지하고 일반적으로 메서드 중 하나를 호출하여 상태 변경을 자동으로 알리는 소프트웨어 디자인 패턴입니다.
|
||||
|
||||
**프로그램 코드 예제**
|
||||
|
||||
먼저 `WeatherObserver` 인터페이스와 우리의 종족 `Orcs` 와 `Hobbits` 소개하겠습니다.
|
||||
|
||||
```java
|
||||
public interface WeatherObserver {
|
||||
|
||||
void update(WeatherType currentWeather);
|
||||
}
|
||||
|
||||
public class Orcs implements WeatherObserver {
|
||||
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(Orcs.class);
|
||||
|
||||
@Override
|
||||
public void update(WeatherType currentWeather) {
|
||||
LOGGER.info("The orcs are facing " + currentWeather.getDescription() + " weather now");
|
||||
}
|
||||
}
|
||||
|
||||
public class Hobbits implements WeatherObserver {
|
||||
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(Hobbits.class);
|
||||
|
||||
@Override
|
||||
public void update(WeatherType currentWeather) {
|
||||
switch (currentWeather) {
|
||||
LOGGER.info("The hobbits are facing " + currentWeather.getDescription() + " weather now");
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
그리고 끊임없이 변화하는 `Weather` 가 있습니다.
|
||||
|
||||
```java
|
||||
public class Weather {
|
||||
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(Weather.class);
|
||||
|
||||
private WeatherType currentWeather;
|
||||
private final List<WeatherObserver> observers;
|
||||
|
||||
public Weather() {
|
||||
observers = new ArrayList<>();
|
||||
currentWeather = WeatherType.SUNNY;
|
||||
}
|
||||
|
||||
public void addObserver(WeatherObserver obs) {
|
||||
observers.add(obs);
|
||||
}
|
||||
|
||||
public void removeObserver(WeatherObserver obs) {
|
||||
observers.remove(obs);
|
||||
}
|
||||
|
||||
/**
|
||||
* Makes time pass for weather.
|
||||
*/
|
||||
public void timePasses() {
|
||||
var enumValues = WeatherType.values();
|
||||
currentWeather = enumValues[(currentWeather.ordinal() + 1) % enumValues.length];
|
||||
LOGGER.info("The weather changed to {}.", currentWeather);
|
||||
notifyObservers();
|
||||
}
|
||||
|
||||
private void notifyObservers() {
|
||||
for (var obs : observers) {
|
||||
obs.update(currentWeather);
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
여기에 전체 예제가 있습니다.
|
||||
|
||||
```java
|
||||
var weather = new Weather();
|
||||
weather.addObserver(new Orcs());
|
||||
weather.addObserver(new Hobbits());
|
||||
weather.timePasses();
|
||||
weather.timePasses();
|
||||
weather.timePasses();
|
||||
weather.timePasses();
|
||||
```
|
||||
|
||||
프로그램 출력 :
|
||||
|
||||
```
|
||||
The weather changed to rainy.
|
||||
The orcs are facing rainy weather now
|
||||
The hobbits are facing rainy weather now
|
||||
The weather changed to windy.
|
||||
The orcs are facing windy weather now
|
||||
The hobbits are facing windy weather now
|
||||
The weather changed to cold.
|
||||
The orcs are facing cold weather now
|
||||
The hobbits are facing cold weather now
|
||||
The weather changed to sunny.
|
||||
The orcs are facing sunny weather now
|
||||
The hobbits are facing sunny weather now
|
||||
```
|
||||
|
||||
## 클래스 다이어그램
|
||||
|
||||

|
||||
|
||||
## 적용 가능성
|
||||
|
||||
다음 상황에서 관찰자 패턴을 사용하십시오.
|
||||
|
||||
- 추상화에 두 가지 측면이 있을 때 하나는 다른 하나에 종속됩니다. 이러한 측면을 별도의 개체에 캡슐화하면 독립적으로 변경하고 재사용 할 수 있습니다.
|
||||
- 한 개체를 변경하려면 얼마나 다른 개체를 변경해야 하는지 알 수 없는 경우입니다.
|
||||
- 개체가 다른 개체가 누구인지 가정하지 않고 알릴 수 있어야하는 경우. 즉, 개체가 단단히 결합되는 것을 원하지 않습니다.
|
||||
|
||||
## 일반적인 사용 사례
|
||||
|
||||
- 한 개체를 변경하면 다른 개체도 변경됩니다.
|
||||
|
||||
## 실제 사례
|
||||
|
||||
- [java.util.Observer](http://docs.oracle.com/javase/8/docs/api/java/util/Observer.html)
|
||||
- [java.util.EventListener](http://docs.oracle.com/javase/8/docs/api/java/util/EventListener.html)
|
||||
- [javax.servlet.http.HttpSessionBindingListener](http://docs.oracle.com/javaee/7/api/javax/servlet/http/HttpSessionBindingListener.html)
|
||||
- [RxJava](https://github.com/ReactiveX/RxJava)
|
||||
|
||||
## 크레딧
|
||||
|
||||
- [Design Patterns: Elements of Reusable Object-Oriented Software](https://www.amazon.com/gp/product/0201633612/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0201633612&linkCode=as2&tag=javadesignpat-20&linkId=675d49790ce11db99d90bde47f1aeb59)
|
||||
- [Java Generics and Collections](https://www.amazon.com/gp/product/0596527756/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596527756&linkCode=as2&tag=javadesignpat-20&linkId=246e5e2c26fe1c3ada6a70b15afcb195)
|
||||
- [Head First Design Patterns: A Brain-Friendly Guide](https://www.amazon.com/gp/product/0596007124/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596007124&linkCode=as2&tag=javadesignpat-20&linkId=6b8b6eea86021af6c8e3cd3fc382cb5b)
|
||||
- [Refactoring to Patterns](https://www.amazon.com/gp/product/0321213351/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0321213351&linkCode=as2&tag=javadesignpat-20&linkId=2a76fcb387234bc71b1c61150b3cc3a7)
|
@@ -1,87 +0,0 @@
|
||||
---
|
||||
layout: pattern
|
||||
title: Prototype
|
||||
folder: prototype
|
||||
permalink: "/patterns/prototype/"
|
||||
categories: Creational
|
||||
tags:
|
||||
- Gang Of Four
|
||||
- Instantiation
|
||||
---
|
||||
|
||||
## 의도
|
||||
|
||||
prototype 인스턴스를 사용하여 만들 개체의 종류를 지정하고 prototype을 복사하여 새 개체를 만듭니다.
|
||||
|
||||
## 설명
|
||||
|
||||
먼저 성능 이점을 얻기 위해 prototype 패턴이 사용되지 않는다는 점에 유의해야합니다. 오직 prototype 인스턴스에서 새 개체를 만드는 데만 사용됩니다.
|
||||
|
||||
예시
|
||||
|
||||
> 복제된 양인 돌리에 대해 기억나십니까? 자세한 내용은 다루지 않겠습니다만 여기서 핵심은 복제에 관한 것입니다.
|
||||
|
||||
평범한 말하자면
|
||||
|
||||
> 복제를 통해 기존 개체를 기반으로 개체를 만듭니다.
|
||||
|
||||
Wikipedia 말에 의하면
|
||||
|
||||
> prototype 패턴은 소프트웨어 개발에서 생성 디자인 패턴입니다. 생성 할 개체의 유형이 새 개체를 생성하기 위해 복제되는 prototype 인스턴스에 의해 결정될 때 사용됩니다.
|
||||
|
||||
간단히 말해, 객체를 처음부터 만들고 설정하는 문제를 겪는 대신 기존 객체의 복사본을 만들어 필요에 맞게 수정할 수 있습니다.
|
||||
|
||||
**프로그램 코드 예제**
|
||||
|
||||
Java에서는 `Cloneable` 을 구현하고 `Object` 에서 `clone` 을 오버라이딩하여 쉽게 수행 할 수 있습니다.
|
||||
|
||||
```java
|
||||
class Sheep implements Cloneable {
|
||||
private String name;
|
||||
public Sheep(String name) { this.name = name; }
|
||||
public void setName(String name) { this.name = name; }
|
||||
public String getName() { return name; }
|
||||
@Override
|
||||
public Sheep clone() {
|
||||
try {
|
||||
return (Sheep)super.clone();
|
||||
} catch(CloneNotSuportedException) {
|
||||
throw new InternalError();
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
그런 다음 아래와 같이 복제할 수 있습니다.
|
||||
|
||||
```java
|
||||
var original = new Sheep("Jolly");
|
||||
System.out.println(original.getName()); // Jolly
|
||||
|
||||
// Clone and modify what is required
|
||||
var cloned = original.clone();
|
||||
cloned.setName("Dolly");
|
||||
System.out.println(cloned.getName()); // Dolly
|
||||
```
|
||||
|
||||
## 클래스 다이어그램
|
||||
|
||||

|
||||
|
||||
## 적용 가능성
|
||||
|
||||
시스템이 제품의 생성, 구성, 표현 및 표현 방식에 독립적이어야 할 때 prototype 패턴을 사용
|
||||
|
||||
- 인스턴스화할 클래스가 런타임에 지정되는 경우 (예 : 동적 로딩)
|
||||
- 제품의 클래스 계층 구조와 유사한 팩토리의 클래스 계층 구조 구축을 방지해야할 경우
|
||||
- 클래스의 인스턴스가 몇 가지 다른 상태 조합 중 하나만 가질 수 있는 경우. 적절한 상태로 매번 클래스를 수동으로 인스턴스화하는 것보다 해당하는 수의 prototype을 설치하고 복제하는 것이 더 편리 할 수 있습니다.
|
||||
- 복제에 비해 개체 생성 비용이 많이 드는 경우.
|
||||
|
||||
## 실제 사례
|
||||
|
||||
- [java.lang.Object#clone()](https://docs.oracle.com/javase/8/docs/api/java/lang/Object.html#clone%28%29)
|
||||
|
||||
## 크레딧
|
||||
|
||||
- [Design Patterns: Elements of Reusable Object-Oriented Software](https://www.amazon.com/gp/product/0201633612/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0201633612&linkCode=as2&tag=javadesignpat-20&linkId=675d49790ce11db99d90bde47f1aeb59)
|
||||
- [Head First Design Patterns: A Brain-Friendly Guide](https://www.amazon.com/gp/product/0596007124/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596007124&linkCode=as2&tag=javadesignpat-20&linkId=6b8b6eea86021af6c8e3cd3fc382cb5b)
|
@@ -1,84 +0,0 @@
|
||||
---
|
||||
layout: pattern
|
||||
title: Singleton
|
||||
folder: singleton
|
||||
permalink: "/patterns/singleton/"
|
||||
categories: Creational
|
||||
tags:
|
||||
- Gang of Four
|
||||
---
|
||||
|
||||
## 의도
|
||||
|
||||
클래스에 인스턴스가 하나만 있는지 확인하고 이에 대한 전역 access point을 제공합니다.
|
||||
|
||||
## 설명
|
||||
|
||||
예시
|
||||
|
||||
> 마법사들이 마법을 연구하는 상아탑은 단 하나뿐입니다. 마법사는 항상 동일한 마법의 상아탑을 사용합니다. 여기서 상아탑은 singleton입니다.
|
||||
|
||||
평범하게 말하자면
|
||||
|
||||
> 특정 클래스의 개체가 하나만 생성되도록합니다.
|
||||
|
||||
Wikipedia 말에 의하면
|
||||
|
||||
> 소프트웨어 엔지니어링에서 singleton 패턴은 클래스의 인스턴스화를 하나의 객체로 제한하는 소프트웨어 디자인 패턴입니다. 이는 시스템 전체에서 작업을 조정하는 데 정확히 하나의 개체가 필요할 때 유용합니다.
|
||||
|
||||
**프로그램 코드 예제**
|
||||
|
||||
Joshua Bloch, Effective Java 2nd Edition p.18
|
||||
|
||||
> 단일 요소 열거형은 singleton을 구현하는 가장 좋은 방법입니다.
|
||||
|
||||
```java
|
||||
public enum EnumIvoryTower {
|
||||
INSTANCE
|
||||
}
|
||||
```
|
||||
|
||||
그런 다음 사용하려면 :
|
||||
|
||||
```java
|
||||
var enumIvoryTower1 = EnumIvoryTower.INSTANCE;
|
||||
var enumIvoryTower2 = EnumIvoryTower.INSTANCE;
|
||||
assertEquals(enumIvoryTower1, enumIvoryTower2); // true
|
||||
```
|
||||
|
||||
## 클래스 다이어그램
|
||||
|
||||

|
||||
|
||||
## 적용 가능성
|
||||
|
||||
다음과 같은 경우 Singleton 패턴을 사용합니다.
|
||||
|
||||
- 정확히 하나의 클래스 인스턴스가 있어야하며 잘 알려진 access point에서 클라이언트에 접근할 수 있어야합니다.
|
||||
- 단일 인스턴스가 서브 클래싱으로 확장 가능해야하고 클라이언트가 코드를 수정하지 않고 확장 인스턴스를 사용할 수 있어야 하는 경우
|
||||
|
||||
## 일반적인 사용 사례
|
||||
|
||||
- 로깅 클래스
|
||||
- 데이터베이스에 대한 연결 관리
|
||||
- 파일 관리자
|
||||
|
||||
## 실제 사례
|
||||
|
||||
- [java.lang.Runtime#getRuntime()](http://docs.oracle.com/javase/8/docs/api/java/lang/Runtime.html#getRuntime%28%29)
|
||||
- [java.awt.Desktop#getDesktop()](http://docs.oracle.com/javase/8/docs/api/java/awt/Desktop.html#getDesktop--)
|
||||
- [java.lang.System#getSecurityManager()](http://docs.oracle.com/javase/8/docs/api/java/lang/System.html#getSecurityManager--)
|
||||
|
||||
## 결과
|
||||
|
||||
- 자체 생성 및 수명주기를 제어하여 SRP (Single Responsibility Principle)를 위반합니다.
|
||||
- 이 개체가 사용하는 개체와 리소스가 할당 해제되는 것을 방지하는 전역 공유 인스턴스를 사용하도록 권장합니다.
|
||||
- 밀접하게 연결된 코드를 만듭니다. Singleton의 클라이언트는 테스트하기가 어려워집니다.
|
||||
- Singleton의 하위 클래스를 만드는 것이 거의 불가능합니다.
|
||||
|
||||
## 크레딧
|
||||
|
||||
- [Design Patterns: Elements of Reusable Object-Oriented Software](https://www.amazon.com/gp/product/0201633612/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0201633612&linkCode=as2&tag=javadesignpat-20&linkId=675d49790ce11db99d90bde47f1aeb59)
|
||||
- [Effective Java](https://www.amazon.com/gp/product/0134685997/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0134685997&linkCode=as2&tag=javadesignpat-20&linkId=4e349f4b3ff8c50123f8147c828e53eb)
|
||||
- [Head First Design Patterns: A Brain-Friendly Guide](https://www.amazon.com/gp/product/0596007124/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596007124&linkCode=as2&tag=javadesignpat-20&linkId=6b8b6eea86021af6c8e3cd3fc382cb5b)
|
||||
- [Refactoring to Patterns](https://www.amazon.com/gp/product/0321213351/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0321213351&linkCode=as2&tag=javadesignpat-20&linkId=2a76fcb387234bc71b1c61150b3cc3a7)
|
2
pom.xml
2
pom.xml
@@ -195,11 +195,9 @@
|
||||
<module>strangler</module>
|
||||
<module>arrange-act-assert</module>
|
||||
<module>transaction-script</module>
|
||||
<module>registry</module>
|
||||
<module>filterer</module>
|
||||
<module>factory</module>
|
||||
<module>separated-interface</module>
|
||||
<module>data-transfer-object-enum-impl</module>
|
||||
</modules>
|
||||
|
||||
<repositories>
|
||||
|
@@ -1,86 +0,0 @@
|
||||
---
|
||||
layout: pattern
|
||||
title: Registry
|
||||
folder: registry
|
||||
permalink: /patterns/registry/
|
||||
categories: Creational
|
||||
tags:
|
||||
- Instantiation
|
||||
---
|
||||
|
||||
## Intent
|
||||
Stores the objects of a single class and provide a global point of access to them.
|
||||
Similar to Multiton pattern, only difference is that in a registry there is no restriction on the number of objects.
|
||||
|
||||
## Explanation
|
||||
|
||||
In Plain Words
|
||||
|
||||
> Registry is a well-known object that other objects can use to find common objects and services.
|
||||
|
||||
**Programmatic Example**
|
||||
Below is a `Customer` Class
|
||||
|
||||
```java
|
||||
public class Customer {
|
||||
|
||||
private final String id;
|
||||
private final String name;
|
||||
|
||||
public Customer(String id, String name) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public String getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
}
|
||||
```
|
||||
|
||||
This registry of the `Customer` objects is `CustomerRegistry`
|
||||
```java
|
||||
public final class CustomerRegistry {
|
||||
|
||||
private static final CustomerRegistry instance = new CustomerRegistry();
|
||||
|
||||
public static CustomerRegistry getInstance() {
|
||||
return instance;
|
||||
}
|
||||
|
||||
private final Map<String, Customer> customerMap;
|
||||
|
||||
private CustomerRegistry() {
|
||||
customerMap = new ConcurrentHashMap<>();
|
||||
}
|
||||
|
||||
public Customer addCustomer(Customer customer) {
|
||||
return customerMap.put(customer.getId(), customer);
|
||||
}
|
||||
|
||||
public Customer getCustomer(String id) {
|
||||
return customerMap.get(id);
|
||||
}
|
||||
|
||||
}
|
||||
```
|
||||
|
||||
## Class diagram
|
||||

|
||||
|
||||
## Applicability
|
||||
Use Registry pattern when
|
||||
|
||||
* client wants reference of some object, so client can lookup for that object in the object's registry.
|
||||
|
||||
## Consequences
|
||||
Large number of bulky objects added to registry would result in a lot of memory consumption as objects in the registry are not garbage collected.
|
||||
|
||||
## Credits
|
||||
* https://www.martinfowler.com/eaaCatalog/registry.html
|
||||
* https://wiki.c2.com/?RegistryPattern
|
Binary file not shown.
Before Width: | Height: | Size: 16 KiB |
@@ -1,21 +0,0 @@
|
||||
@startuml
|
||||
package com.iluwatar.registry {
|
||||
class App {
|
||||
- LOGGER : Logger {static}
|
||||
+ App()
|
||||
+ main(args : String[]) {static}
|
||||
}
|
||||
class Customer {
|
||||
- id : String
|
||||
- name : String
|
||||
+ getId() : String
|
||||
+ getName() : String
|
||||
+ toString() : String
|
||||
}
|
||||
class CustomerRegistry {
|
||||
+ addCustomer(customer : Customer)
|
||||
+ getCustomer(id : String)
|
||||
}
|
||||
}
|
||||
Customer --> "-addCustomer" CustomerRegistry
|
||||
@enduml
|
@@ -1,46 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<parent>
|
||||
<groupId>com.iluwatar</groupId>
|
||||
<artifactId>java-design-patterns</artifactId>
|
||||
<version>1.24.0-SNAPSHOT</version>
|
||||
</parent>
|
||||
<artifactId>registry</artifactId>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.junit.jupiter</groupId>
|
||||
<artifactId>junit-jupiter-engine</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>junit</groupId>
|
||||
<artifactId>junit</artifactId>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-assembly-plugin</artifactId>
|
||||
<executions>
|
||||
<execution>
|
||||
<configuration>
|
||||
<archive>
|
||||
<manifest>
|
||||
<mainClass>com.iluwatar.registry.App</mainClass>
|
||||
</manifest>
|
||||
</archive>
|
||||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
</project>
|
@@ -1,27 +0,0 @@
|
||||
package com.iluwatar.registry;
|
||||
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
public class App {
|
||||
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(App.class);
|
||||
|
||||
/**
|
||||
* Program entry point.
|
||||
*
|
||||
* @param args command line args
|
||||
*/
|
||||
public static void main(String[] args) {
|
||||
CustomerRegistry customerRegistry = CustomerRegistry.getInstance();
|
||||
var john = new Customer("1", "John");
|
||||
customerRegistry.addCustomer(john);
|
||||
|
||||
var julia = new Customer("2", "Julia");
|
||||
customerRegistry.addCustomer(julia);
|
||||
|
||||
LOGGER.info("John {}", customerRegistry.getCustomer("1"));
|
||||
LOGGER.info("Julia {}", customerRegistry.getCustomer("2"));
|
||||
}
|
||||
|
||||
}
|
@@ -1,28 +0,0 @@
|
||||
package com.iluwatar.registry;
|
||||
|
||||
public class Customer {
|
||||
|
||||
private final String id;
|
||||
private final String name;
|
||||
|
||||
public Customer(String id, String name) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public String getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "Customer{"
|
||||
+ "id='" + id + '\''
|
||||
+ ", name='" + name + '\''
|
||||
+ '}';
|
||||
}
|
||||
}
|
@@ -1,28 +0,0 @@
|
||||
package com.iluwatar.registry;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
|
||||
public final class CustomerRegistry {
|
||||
|
||||
private static final CustomerRegistry instance = new CustomerRegistry();
|
||||
|
||||
public static CustomerRegistry getInstance() {
|
||||
return instance;
|
||||
}
|
||||
|
||||
private final Map<String, Customer> customerMap;
|
||||
|
||||
private CustomerRegistry() {
|
||||
customerMap = new ConcurrentHashMap<>();
|
||||
}
|
||||
|
||||
public Customer addCustomer(Customer customer) {
|
||||
return customerMap.put(customer.getId(), customer);
|
||||
}
|
||||
|
||||
public Customer getCustomer(String id) {
|
||||
return customerMap.get(id);
|
||||
}
|
||||
|
||||
}
|
@@ -1,44 +0,0 @@
|
||||
package com.iluwatar.registry;
|
||||
|
||||
import org.junit.jupiter.api.BeforeAll;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
import static org.junit.jupiter.api.Assertions.assertNotNull;
|
||||
import static org.junit.jupiter.api.Assertions.assertNull;
|
||||
|
||||
public class CustomerRegistryTest {
|
||||
|
||||
private static CustomerRegistry customerRegistry;
|
||||
|
||||
@BeforeAll
|
||||
public static void setUp() {
|
||||
customerRegistry = CustomerRegistry.getInstance();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldBeAbleToAddAndQueryCustomerObjectFromRegistry() {
|
||||
Customer john = new Customer("1", "john");
|
||||
Customer julia = new Customer("2", "julia");
|
||||
|
||||
customerRegistry.addCustomer(john);
|
||||
customerRegistry.addCustomer(julia);
|
||||
|
||||
Customer customerWithId1 = customerRegistry.getCustomer("1");
|
||||
assertNotNull(customerWithId1);
|
||||
assertEquals("1", customerWithId1.getId());
|
||||
assertEquals("john", customerWithId1.getName());
|
||||
|
||||
Customer customerWithId2 = customerRegistry.getCustomer("2");
|
||||
assertNotNull(customerWithId2);
|
||||
assertEquals("2", customerWithId2.getId());
|
||||
assertEquals("julia", customerWithId2.getName());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldReturnNullWhenQueriedCustomerIsNotInRegistry() {
|
||||
Customer customerWithId5 = customerRegistry.getCustomer("5");
|
||||
assertNull(customerWithId5);
|
||||
}
|
||||
|
||||
}
|
Reference in New Issue
Block a user