DevEnjoy

One Step Closer

Object Oriented Programming SOLID

2016년 7월 7일 by YongPwi Leave a Comment

기초 공부를 생각하다 문뜩,,,

명확하게 모르는것 같아서 정리,,,

1. Single Responsibility Principle(단일 책임 원칙)

객체는 단 하나의 책임만 가져야 한다.

잘못된 예

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
class Text {
    String text;
    String author;
    int length;
 
    String getText() { ... }
    void setText(String s) { ... }
    String getAuthor() { ... }
    void setAuthor(String s) { ... }
    int getLength() { ... }
    void setLength(int k) { ... }
 
    /*methods that change the text*/
    void allLettersToUpperCase() { ... }
    void findSubTextAndDelete(String s) { ... }
 
    /*method for formatting output*/
    void printText() { ... }
}

Text class는 text를 출력하는 처리를 하고 있다. 하지만 출력 기능에 대한 변화가 이루어 지게 된다면 Text class는 계속하여 변경 되어야 한다.
Text class는 다른 역할을 하는 코드들과 결합 관계를 가지게 된다는 뜻
출력 기능을 제거하고 다른 class에서 해당 기능을 처리 하도록 하자.

수정 예

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
class Text {
    String text;
    String author;
    int length;
 
    String getText() { ... }
    void setText(String s) { ... }
    String getAuthor() { ... }
    void setAuthor(String s) { ... }
    int getLength() { ... }
    void setLength(int k) { ... }
 
    /*methods that change the text*/
    void allLettersToUpperCase() { ... }
    void findSubTextAndDelete(String s) { ... }
 
    /*method for formatting output*/
    void printText() { ... }
}

class Print {
    Text text;
 
    Printer(Text t) {
       this.text = t;
    }
 
    void printText() { ... }
}

2. Open / Closed(개방 폐쇠 원칙)

특정 클래스는 그 클래스를 수정하지 않으면서 확장(extension) 가능해야 한다

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
public class FacebookUser{
 
    public boolean isValidUser() {
        System.out.println("FacebookUser: valid user...");
        /*Logic to valid user*/
        return true;
    }
}

// UserRegisterManager class에 addUser(TwitterUser user) method가 추가될때 추가 되어야 하는 class
//public class TwitterUser{
//
//    public boolean isValidUser() {
//        System.out.println("FacebookUser: valid user...");
//        /*Logic to valid user*/
//        return true;
//    }
//}

public class UserRegisterManager {
 
    public void addUser (FacebookUser user) {
        if(user.isValidUser()) {
            System.out.println("UserRegisterManager: valid user.");
        }
    }

    // 추가 되는 method
    public void addUser (TwitterUser user) {
        if(user.isValidUser()) {
            System.out.println("UserRegisterManager: valid user.");
        }
    }
}

UserRegisterManager class에 addUser (TwitterUser user) method가 추가되어야 한다고 가정한다.
새로운 기능에 대한 지원을 추가하기 위해 클래스를 수정해야합니다. 사실, 우리는 우리가 ClaimApprovalManager 클래스를 수정 할 때 이미 쓴 첫 번째 인스턴스에 개방 폐쇄 원칙을 위반했다. 변화가 많은 시스템일 경우 변경에 주의를 기울어야 할 부분이 많아진다.
응용 프로그램이 취약하고 확장하는 비용 발생하며 오류가 발생할 확률이 높아진다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
public abstract class User {
    public abstract boolean isValidUser();
}

public class FacebookUser extends User{
    public boolean isValidUser(){
        System.out.println("FacebookUser: valid user...");
        /*Logic to valid user*/
        return true;
    }
 
}

public class TwitterUser extends User{
    public boolean isValidUser(){
        System.out.println("TwitterUser: valid user...");
        /*Logic to valid user*/
        return true;
    }
 
}

public class UserRegisterManager {
    public void processClaim(User user){
        if(user.isValidUser()){
            System.out.println("UserRegisterManager: valid user");
        }
    }
 
}

3. 리스코프 치환 원칙(Liskov Substitution Principle)

서브타입은 언제나 자신이 기반타입 (base type)으로 교체할 수 있어야 한다.

LSP란 상위형 P가 있고 이걸 확장하는 하위형 C가 있을 때 P를 C로 치환할 수 있어야 한다 는 말이다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
class TransportationDevice {
   String name;
   String getName() { ... }
   void setName(String n) { ... }
 
   double speed;
   double getSpeed() { ... }
   void setSpeed(double d) { ... }
   
   Engine engine;
   Engine getEngine() { ... }
   void setEngine(Engine e) { ... }
 
   void startEngine() { ... }
}

class Car extends TransportationDevice {
   @Override
   void startEngine() { ... }
}

상위 코드는 문제가 없다. 자동차는 확실히 운송장치이며, 여기에 우리는 슈퍼 클래스의 startEngine() method를 override 하였다.

다른 운송장치를 추가 해보도록 하자.

1
2
3
4
class Bicycle extends TransportationDevice {
   @Override
   void startEngine() /*problem!*/
}

추가한 운송장치를 보면 자전거는 엔진을 가지고 있지 않으며 엔진을 시작 할 수 없다.

수정을 해보자.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
class TransportationDevice {
   String name;
   String getName() { ... }
   void setName(String n) { ... }
 
   double speed;
   double getSpeed() { ... }
   void setSpeed(double d) { ... }

   //engine 관련 정보 삭제
}

class DevicesWithoutEngines extends TransportationDevice {  
   void startMoving() { ... }
}

class DevicesWithEngines extends TransportationDevice {  
   Engine engine;
   Engine getEngine() { ... }
   void setEngine(Engine e) { ... }
 
   void startEngine() { ... }
}

class Car extends DevicesWithEngines {
   @Override
   void startEngine() { ... }
}

class Bicycle extends DevicesWithoutEngines {
   @Override
   void startMoving() { ... }
}

4.Interface Segregation Principle(인터페이스 분리 원칙)
client는 자신이 사용하는 interface의 변경으로 자신을 변경하는 것은 용납하지만 자신과 관련되지 않는 interface의 변화로 인해 자신이 변하는 것은 용납해서는 안된다.
하나의 일반적인 interface 보다 구체적인 여러 개의 Interface가 낫다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
public interface Toy {
    void setPrice(double price);
    void setColor(String color);
    void move();
    void fly();
}

public class ToyHouse implements Toy {
    double price;
    String color;
   
    @Override
    public void setPrice(double price) {
        this.price = price;
    }
   
    @Override
    public void setColor(String color) {
        this.color=color;
    }
   
    @Override
    public void move(){}
    @Override
    public void fly(){}    
}

상위 코드를 보면 Toy interface를 상속받은 ToyHouse는 move(), fly() methode를 사용하지 않아도 구현해야만 한다.
이러한 위반은 코드의 가독성과 개발자를 혼란스럽게 한다.

1
2
3
4
5
6
7
8
9
10
11
12
13
public interface Toy {
     void setPrice(double price);
     void setColor(String color);
}

// interface를 작게 분리한다.
public interface Movable {
    void move();
}

public interface Flyable {
    void fly();
}

인터페이스를 작게 분리 하였으면 각 필요한 class의 기능들을 구현한다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
public class ToyHouse implements Toy {
    double price;
    String color;
 
    @Override
    public void setPrice(double price) {
 
        this.price = price;
    }
    @Override
    public void setColor(String color) {
 
        this.color=color;
    }
    @Override
    public String toString(){
        return "ToyHouse: Toy house- Price: "+price+" Color: "+color;
    }
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
public class ToyPlane implements Toy, Movable, Flyable {
    double price;
    String color;
 
    @Override
    public void setPrice(double price) {
        this.price = price;
    }
 
    @Override
    public void setColor(String color) {
        this.color=color;
    }
    @Override
    public void move(){
 
        System.out.println("ToyPlane: Start moving plane.");
    }
    @Override
    public void fly(){
 
        System.out.println("ToyPlane: Start flying plane.");
    }
    @Override
    public String toString(){
        return "ToyPlane: Moveable and flyable toy plane- Price: "+price+" Color: "+color;
    }
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
public class ToyBuilder {
    public static ToyHouse buildToyHouse(){
        ToyHouse toyHouse=new ToyHouse();
        toyHouse.setPrice(15.00);
        toyHouse.setColor("green");
        return toyHouse;
        }
    public static ToyCar buildToyCar(){
        ToyCar toyCar=new ToyCar();
        toyCar.setPrice(25.00);
        toyCar.setColor("red");
        toyCar.move();
        return toyCar;
    }
    public static ToyPlane buildToyPlane(){
        ToyPlane toyPlane=new ToyPlane();
        toyPlane.setPrice(125.00);
        toyPlane.setColor("white");
        toyPlane.move();
        toyPlane.fly();
        return toyPlane;
    }
}

5.Dependency Inversion Principle(의존 역전 원칙)

구현 클래스가 아닌 인터페이스 타입을 사용하라는 규칙이다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
public class LightBulb {
    public void turnOn() {
        System.out.println("LightBulb: Bulb turned on...");
    }
    public void turnOff() {
        System.out.println("LightBulb: Bulb turned off...");
    }
}

public class ElectricPowerSwitch {
    public LightBulb lightBulb;
    public boolean on;
    public ElectricPowerSwitch(LightBulb lightBulb) {
        this.lightBulb = lightBulb;
        this.on = false;
    }
    public boolean isOn() {
        return this.on;
    }
    public void press(){
        boolean checkOn = isOn();
        if (checkOn) {
            lightBulb.turnOff();
            this.on = false;
        } else {
            lightBulb.turnOn();
            this.on = true;
        }
 
    }
}

상위 코드에서 ElectricPowerSwitch class에 LightBulb class의 참조 필드를 사용하였다. ElectricPowerSwitch 생성자에서 lightBulb 객체를 생성하고 필드에 할당한다. 그 다음 ElectricPowerSwitch의 상태를 반환하는 isOn() method를 사용하였다. press() method에 state를 기준으로 turnOn() 및 turnOff() method를 호출한다.
상위 코드로 우리는 switch를 끄고 켤수 있다. 그러나 고레벨에 있는 ElectricPowerSwitch class는 저레벨의 LightBulb class를 직접 참조한다. 고레벨과 저레벨의 차이는 여러가지 일을 복합적으로 한다면 고레벨(ex:파일을 불러와 암호화 여부를 확인하고 backup 폴더에 저장하고 경로를 json으로 전달 해준다.), 저레벨은 단순한 기능만을 한다(ex:파일에서 바이트 데이터를 읽어온다.)

문제를 해결하기 위해서 인터페이스를 만들고 ElectricPowerSwitch, LightBulb classes를 구현한다.

1
2
3
4
5
6
7
8
9
public interface Switch {
    boolean isOn();
    void press();
}

public interface Switchable {
    void turnOn();
    void turnOff();
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
public class ElectricPowerSwitch implements Switch {
    public Switchable client;
    public boolean on;
    public ElectricPowerSwitch(Switchable client) {
        this.client = client;
        this.on = false;
    }
    public boolean isOn() {
        return this.on;
    }
   public void press(){
       boolean checkOn = isOn();
       if (checkOn) {
           client.turnOff();
           this.on = false;
       } else {
             client.turnOn();
             this.on = true;
       }
 
   }
}
1
2
3
4
5
6
7
8
9
10
11
public class LightBulb implements Switchable {
    @Override
    public void turnOn() {
        System.out.println("LightBulb: Bulb turned on...");
    }
 
    @Override
    public void turnOff() {
        System.out.println("LightBulb: Bulb turned off...");
    }
}
1
2
3
4
5
6
7
8
9
10
11
public class Fan implements Switchable {
    @Override
    public void turnOn() {
        System.out.println("Fan: Fan turned on...");
    }
 
    @Override
    public void turnOff() {
        System.out.println("Fan: Fan turned off...");
    }
}

Single Responsibility Prinsciple

Open / Closed

Liskov Substitution Principle

Interface Segregation Principle

Dependency Inversion Principle

Posted in: Java, Programing Tagged: JAVA, OOP, SOLID

os x nano editor color 설정

2016년 6월 19일 by YongPwi 1 Comment

os xdㅔ서 nano editor 사용시 color 설정 부분에 대한 정보가 많지 않아서

답답했는데,,,

오늘 날잡고 세팅을 하고 혹시 몰라서 정리한다.

먼저 OS X Nano editor을 확인하고 업데이트 한다.

1
nano -V

2016.06.19일 기준으로 가장 최신 버전은 2.2.6 이다.

http://nano-editor.org/download.php 여기서 확인 가능

그리고 기본 terminal 프로그램으로 하위 명령어로 최신 파일 다운 및 설치를 진행!(iterm에서 진행하면 안되더라,,,)

1
2
3
4
5
6
7
cd Downloads
wget http://www.nano-editor.org/dist/v2.2/nano-2.2.6.tar.gz
tar -xzvf nano* && rm nano-2.2.6.tar.gz
cd nano-2.2.6 && ls -al
./configure
sudo make
sudo make install

설치가 끝나면 nano editor의 경로 및 버전 확인한다.

1
2
3
which nano

nano -V

/usr/local/bin/nano

2.2.6

상위 경로로 나오면 정상적으로 설치 되었다.

그리고 $HOME 경로로 이동하여서 .nanorc 설정 파일을 생성 및 수정한다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
nano ~/.nanorc

include "/usr/local/share/nano/nanorc.nanorc"
 # Alphabetically
include "/usr/local/share/nano/awk.nanorc"
include "/usr/local/share/nano/asm.nanorc"
include "/usr/local/share/nano/c.nanorc"
include "/usr/local/share/nano/css.nanorc"
include "/usr/local/share/nano/cmake.nanorc"
include "/usr/local/share/nano/debian.nanorc"
include "/usr/local/share/nano/fortran.nanorc"
include "/usr/local/share/nano/gentoo.nanorc"
include "/usr/local/share/nano/groff.nanorc"
include "/usr/local/share/nano/html.nanorc"
include "/usr/local/share/nano/java.nanorc"
include "/usr/local/share/nano/man.nanorc"
include "/usr/local/share/nano/mutt.nanorc"
include "/usr/local/share/nano/makefile.nanorc"
include "/usr/local/share/nano/ocaml.nanorc"
include "/usr/local/share/nano/objc.nanorc"
include "/usr/local/share/nano/patch.nanorc"
include "/usr/local/share/nano/perl.nanorc"
include "/usr/local/share/nano/python.nanorc"
include "/usr/local/share/nano/php.nanorc"
include "/usr/local/share/nano/pov.nanorc"
include "/usr/local/share/nano/ruby.nanorc"
include "/usr/local/share/nano/sh.nanorc"
include "/usr/local/share/nano/tcl.nanorc"
include "/usr/local/share/nano/tex.nanorc"
include "/usr/local/share/nano/xml.nanorc"

그리고서 정상적으로 적용 되었는지 확인해보자

1
2
3
4
5
// 하단 경로로 이동해서
cd /usr/local/share/nano

//ruby 파일이 정상적으로 열리는지 확인해보자
nano ruby.nanorc

원 글 링크는 하단에 첨부

https://thecustomizewindows.com/2015/01/os-x-nano-syntax-highlighting/

Posted in: OS X Tagged: color, editor, nano, OS X

iterm2 build 3.0에서 Go2Shell 작동 불가 관련

2016년 6월 8일 by YongPwi 2 Comments

iterm2를 사용중에 무심코 업데이트를 하였더니

어느 순간부터 Go2Shell 실행시 해당 경로에서 iterm2이 열리는게 아니고

user 경로에서 열려서 왜 그런가 해서 좀 찾아보니 문제가 있었다.

내가 사용중인 Go2Sheel은 app store에서 다운 받았다.

2015년 이후로 업데이트는 없다,,,

하지만 개발자는 이 사실을 인지하고 수정본을 배포하고 있었다.

사이트에서 다운용 프로그램으로 설치하면

정상 작동한다.

기존 프로그램과 세팅 방법등 먼가 다르긴 한데 기능은 동일하다!

http://comments.gmane.org/gmane.comp.terminal-emulators.iterm2.general/3591

https://gitlab.com/gnachman/iterm2/issues/3320

Posted in: OS X Tagged: Go2Shell, iterm, OS X

Frontend 자동화 도구

2016년 5월 31일 by YongPwi Leave a Comment
  • Yeoman
    • scaffolding tool
      • 조력, 발판
      • 초기 단계에 적절한 도움을 통한 작업시간 단축
    • web appliication 개발 전에 필요한 디렉토리 구조 및 기본적인 파일 생성
    • 목적에 따라 다르게 구조를 잡아준다
      • bootstrap app => bootstrap generator
      • angular js => angular generator
    • install
      • npm(window, linux)
      • node.js, ruby 의존성 때문에 설치 필요
      • // compass를 설치합니다. sass 컴파일 시 필요합니다.

        $ gem install compass

        // Yeoman을 설치합니다.

        $ npm install -g yo

    • generator에 따라 bower.json 자동 생성
      • bower을 사용하여 의존 컴포넌트를 자동으로 받아 scaffoling 생성
      • 추가 컴포넌트 필요시 bower.json에 추가 후 다시 install
    • scaffolding에 맞는 기본 Guntfile.js 자동 생성
      • 추가 task, 변경 필요한 task 존재시 yeoman이 생성한 gruntfile.js에 추가 or 수정
  • Bower(http://bower.io)
    • component 의존성 관리
    • npm, brew 비슷
    • 라이브러리 파일을 형상관리 하지 않아도 됨
  • Grunt, Gulp
    • Grunt(http://gruntjs-kr.herokuapp.com)
      • 자바스크립트 프로젝트를 위한 task 기반의 CLI(command line interface build too)
        • task – static file(js, css, html) concat, miniflcation
        • node.js에서 할수 있는 모느것을 프로젝트에 적용 가능
      • 반복되는 작업을 Gruntflie.js를 작성하여 자동 빌드, 배포
      • node.js 기반, 필수, npm으로 global로 설치해야함
      • grunt는 script파일인 Gruntfile.js를 참고하여 수행
    • Gulp
      • 플러그인을 연결해서 사용
      • node 스럽다.
        • 작은 모듈이 많고 이를 조합해서 테스크를 만든다.
      • 코드로 테스크를 선언

 

참고
http://javarouka.github.io/pt/yeoman
http://mobicon.tistory.com/402
http://e-rooms.tistory.com/entry/프론트-엔드-웹-개발을-위한-빌드-시스템Grunt-Yeoman-Bower
https://blog.outsider.ne.kr/1181?category=20

Posted in: Javascript, Programing Tagged: bower, Frontend, grunt, gulp, yeoman

맥 맞춤법 검사기(미남이님) 검색 주소 변경

2016년 5월 9일 by YongPwi Leave a Comment

잘 사용 중이던 맞춤법 검사기가 얼마 전부터 오류를 내뿜어서,,,

고쳐주겠지 하다가,,, 주소만 변경하면 되지 않을까 싶어서 좀 들여다보았음,,,

/Users/사용자명/Library/Services

경로로 가보면 “✔ 선택한 글의 한국어 맞춤법 검사하기” 파일이 있다,,,

해당 파일의 마우스 오른쪽 버튼을 누르고 “패키지 내용 보기”를 누르고 상세 파일을 보면

/Contents/document.wflow 파일이 있다,,,

해당 파일을 열어보면 63번째 라인에 부산대 맞춤법 검색 주소가 설정되어 있다,,,

1
BASE_URL=http://speller.cs.pusan.ac.kr/PnuSpellerISAPI_201602

이걸 상위처럼 변경하면 정상 작동한다.

부산대 맞춤법 검색이 업데이트되어서 발생한 문제로 확인된다,,,

아마 조만간 미남이님께서 업데이트 하실 것 같은데 급한대로 고쳐서 사용하실 분들은

상위 방법으로 해보시길,,,

참고
미남이님 한국어 맞춤법 검사기 workflow

부산대 맞춤법 검사기

Posted in: OS X, Talk Tagged: OS X, workflow, 맞춤법

Ubuntu Gitlab http 방식으로 사용시 push commit error – Nginx

2016년 2월 25일 by YongPwi Leave a Comment

Ubuntu에 Gitlab을 http 방식으로 사용시

대량의 파일을 push 할 경우 Push large commit over http fails이 발생하게 된다.

원인은 nginx에서 받는 사이즈의 크기가 오버되어서 발생하는 문제이다.

1
2
3
4
5
6
7
8
// nginx 설정 파일 수정 (/etc/nginx/nginx.conf)
sudo nano /etc/nginx/nginx.conf

http {
   // 상위 또는 하단에 추가 해준다. (사이즈는 알아서 적당히~)
   # git http post request error
   client_max_body_size 1000M;
}
Posted in: Gitlab, Nginx, Programing, Ubuntu Tagged: commit, gitlab, nginx, ubuntu

Ubuntu 14.04 Gitlab 설치시 외부 Nginx 설정

2016년 2월 23일 by YongPwi Leave a Comment

Ubuntu 14.04에 Gitlab 설치시 내장되어 있는 nginx가 기본으로 설정된다.

하지만 nginx를 자체적으로 가지고 있을경우 Gitlab 설정에 nginx를 비활성화 시키고

사용하던 nginx에 붙일경우 권한 문제로 연동이 안되는 상황이 발생하였다.

그럴경우 gitlab 설정 파일에 nginx의 user 권한을 수정해주면 정상적으로 연동 가능하다.

1
2
3
4
5
6
7
8
9
// nginx 설정 파일 경로
// apt-get 설치시 default(/etc/nginx/nginx.conf)
sudo nano /etc/nginx/nginx.conf

// default
user  nginx;

// 변경
user www-data;

https://gitlab.com/gitlab-org/omnibus-gitlab/blob/master/doc/settings/nginx.md#using-a-non-bundled-web-server

Posted in: Programing, Ubuntu Tagged: gitlab, nginx, ubuntu

Ubuntu tomcat time 설정

2016년 2월 4일 by YongPwi Leave a Comment

최근에 AWS를 세팅하여서 사용하고 있었는데

처음 서버 세팅을 하여 아무 생각 없이 사용 하였는데 서버 time이 6시간이 느린것을 알게 되었다,,,

별 생각없이 쓰다가 tomcat에 올라간 서비스들의 log를 확인하다 보니 시간이 달라서 꽤나 신경 쓰였다,,,

오늘 생각난 김에 server time 설정하자 라고 해서 작업 했더니

server time은 잘 바뀌었는데 tomcat log에 찍히는 time은 안 바뀌더라,,,

좀 뒤져보다 해결해서 나중을 위해서 정리해 둔다,,,

  • Ubuntu server time 설정
1
sudo ln -sf /usr/share/zoneinfo/Asia/Seoul /etc/localtime
  • tomcat time 설정

tomcat 설치 경로로 가서 bin 폴더 하위에 setenv.sh 파일이 있으면 해당 파일에 없으면 생성하여 환경 설정 해준다.

1
export CATALINA_OPTS=-Duser.timezone=Asia/Seoul
Posted in: Java, Programing Tagged: time, Tomcat, ubuntu

IntelliJ Lombok cannot find symbol 컴파일 에러

2015년 9월 1일 by YongPwi 1 Comment

작업 중 코드상에서는 에러가 없는데,,,

컴파일 시에 Lombak 적용이 되지 않아서 꽤 삽질했는데,,,

역시나 구글링을 해보니,,,

내가 멍청해서 놓쳤던 부분이 있었다,,,

다음 삽질을 방지하기 위하여 정리!!

1
2
3
4
5
6
7
8
9
10
11
12
13
14
@Data
@Entity
public class User {
    @Id
    @Column(nullable = false)
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Integer userId;

    @Column(length = 80, nullable = false, unique = true)
    private String userEmail;

    @Column(length = 255, nullable = false)
    private String userPass;
}

상위 처럼 되어 있는데도 컴파일 시에 에러가 난다,,,

스크린샷 2015-09-01 오전 11.08.42

IntelliJ에 “Enable annotation processing”을 활성화 해주면 해결된다.

경로 (IntelliJ Preferences => Build, Excution, Deployment => Compiler => Annotation Processors)

스크린샷 2015-09-01 오전 11.10.51

Posted in: Java, Programing Tagged: IntelliJ, JAVA, Lombok

Template, Callback

2015년 7월 14일 by YongPwi 2 Comments
  • 클라이언트의 역할은 템플릿 안에서 실행될 로직을 담음 콜백 오브젝트를 만들고, 콜백이 참조할 정보를 제공
  • 만들어진 콜백은 클라이언트가 템플릿의 메소드를 호출할 때 파라미터로 전달
  • 템플릿은 정해진 작업 흐름을 따라 작업을 진행하다가 내부에서 생성한 참조정보를 가지고 콜백 오브젝트 호출
  • 콜백은 클라이언트 메소드에 있는 정보와 템플릿이 제공한 참조정보를 이용해서 작업을 수행하고 그 결과를 다시 템플릿에 돌려줌
  • 템플릿은 콜백이 돌려준 정보를 사용해서 작업을 마저 수행
  • 경우에 따라 최종 결과를 클라이언트에 다시 돌려주기도 한다.
  • 매번 메소드 단위로 사용할 오브젝트를 새롭게 전달 받음
  • 콜백 오브젝트가 내부 클래스로서 자신을 생성한 클라이언트 메소드 내의 정보를 직접 참조
  • 전략 패턴과 DI의 장점을 익명 내부 플래스 사용 전략과 결합한 독특한 활용법

Calculator.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
public class Calculator {
    public Integer calcSum(String filepath) throws IOException{
        // 콜백 오브젝트 생성
        LineCallback<Integer> sumCallback = new LineCallback<Integer>() {
            // 익명 내부 클래스에서 인퍼페이스 메소드 override
            public Integer doSomeThingWithLine(String line, Integer value) {
                return value + Integer.parseInt(line);
            }
        };
        // 템플릿 메소드 호출
        return lineReadTemplate(filepath, sumCallback, 0);
    }

    public Integer calcMultiply(String filepath) throws IOException{
        // 콜백 오브젝트 생성
        LineCallback<Integer> muLineCallback = new LineCallback<Integer>() {
            // 익명 내부 클래스에서 인퍼페이스 메소드 override
            public Integer doSomeThingWithLine(String line, Integer value) {
                return value * Integer.parseInt(line);
            }
        };
        // 템플릿 메소드 호출
        return lineReadTemplate(filepath, muLineCallback, 1);
    }

    // 템플릿 메소드(파라미터로 콜백 오브젝트 받음:callback)
    public <T> T lineReadTemplate(String filepath, LineCallback<T> callback, T initVal) throws IOException{
        BufferedReader br = null;
        try{
            br = new BufferedReader(new FileReader(filepath));
            T res = initVal;
            String line = null;
            while ((line = br.readLine()) != null){
                res = callback.doSomeThingWithLine(line, res);
            }
            return res;
        } catch(IOException e){
            System.out.println(e.getMessage());
            throw e;
        } finally {
            if(br != null){
                try{
                    br.close();
                } catch (IOException e){
                    System.out.println(e.getMessage());
                }
            }
        }
    }
}

LineCallback Interface

1
2
3
public interface LineCallback<T> {
    T doSomeThingWithLine(String line, T value);
}
Posted in: Java, Programing Tagged: Callback, Template
« 이전 1 2 3 4 … 6 다음 »

Calendar

7월 2025
일 월 화 수 목 금 토
« 4월    
 12345
6789101112
13141516171819
20212223242526
2728293031  

Recent Posts

  • ubuntu bastion 설정
  • Spring Boot properties 암호화
  • Git Repository Bitbucket과 Issue Tracker Redmine 연동 설정
  • Spring Security 동일 session 제어
  • Spring @Mock, @Mockbean, @InjectMock

Recent Comments

  • pzotov (Ubuntu 14.04에서 Sonarqube 6.7.1 service 등록)
  • cours de theatre paris (AWS ELB와 Auto Scaling 연동, nginx)
  • bayern munich (IntelliJ EAP Font rendering)
  • camiseta del chelsea (OS X에서 APP 아이콘 변경)
  • cheap football shirts replica (jQuery Ajax에서 json Array 직렬화)

Copyright © [the-year] [site-link].

Powered by [wp-link] and [theme-link].