2025-03-26 java(2)

성현규·2025년 3월 27일
post-thumbnail

1. 병원 입원 시나리오

1-1. main

public class Main {
    public static void main(String[] args) {

        // 객체 생성
        Patient patient = new Patient("홍길동", 35, "복통");
        Staff doctor = new Doctor();
        DiagnosisProcess diagnosis = new GeneralDiagnosis();
        PaymentStrategy payment = new CreditcardPayment();
        Notifiable notifier = new SmsNotifier();

        // 병원 시스템 조립
        HospitalSystem hospital = new HospitalSystem(doctor, diagnosis, payment, notifier);

        // 환자 방문 처리
        hospital.processVisit(patient);
    }
}

1-2. HospitalSystem (파사드구조)

public class HospitalSystem {
    private Staff staff;                       // 접수/진료 조율 시스템, 이들은 staff가 필요함을, 진료절차가 필요함을, 결제와 안내가 필요함을 알고 있다. 구체적인건 모른다. -> 와서 끼워넣어야함. -> 그럼 이거부터 만들면서 해나가야겠네. // 파사드 기법
    private DiagnosisProcess diagnosisProcess;
    private PaymentStrategy paymentStrategy;
    private Notifiable notifiable;

    public HospitalSystem(Staff staff, DiagnosisProcess diagnosisProcess, PaymentStrategy paymentStrategy,
            Notifiable notifiable) {
        this.staff = staff;
        this.diagnosisProcess = diagnosisProcess;
        this.paymentStrategy = paymentStrategy;
        this.notifiable = notifiable;
    }

    public void processVisit(Patient patient){
        patient.showInfo();

        staff.performduty(patient);         // 보통은 이런 역할을 할 수 있는 사람을 부른다. -> 각자의 방식으로 와서 일을 하면된다. 
        diagnosisProcess.runprocess(patient);
        paymentStrategy.pay(15000);
        staff.writeRecord(patient);
        notifiable.notify();
    }
}

1-3. Staff

public interface Staff {  // 인터페이스는 public abstract를 컴파일시 붙여준다.
    void performduty(Patient patient);   // 병원 직원이라는 역할 설정 -> 병원 직원은 환자에게 의료 관련 행위를 할 수 있다.
    void writeRecord(Patient patient);   // datebase에 기록을 할 수 있다.
}                      
  • Doctor
public class Doctor implements Staff {
    
    @Override
    public void performduty(Patient patient){
        System.out.printf("[의사] %s님의 진료를 시작합니다. 증상 %s\n", patient.getName(), patient.getSymptom());
    }

    @Override
    public void writeRecord(Patient patient){
        HospitalDatabase.getInstance().generateReport(patient);
    }
}

1-4. diagnosisProcess (템플릿 구조)

public abstract class DiagnosisProcess { // 템플릿 메서드로 구현 -> 진료순서를 고정함. 
    public final void runprocess(Patient patient){ // 변경되지 않는 진료의 흐름. // 어떤 진료를 하던 이 순서를 따름.
        System.out.println("[진료시작]"+ getType() + "진료 프로세스를 시작합니다.");
        checkVitals(patient);
        interview(patient);
        prescribe(patient);

    }

    protected void checkVitals(Patient Patient){
        System.out.println("바이탈 체크 완료");
    }

    protected abstract void interview(Patient Patient);

    protected abstract void  prescribe(Patient Patient);

    protected abstract String getType();
}
  • generalDiagnosis
public class GeneralDiagnosis extends DiagnosisProcess {

    @Override
    protected String getType() { // 진료의 종류를 제시하는 역할할
        return "일반";
    }

    @Override
    protected void interview(Patient Patient) {
        System.out.println("일반 문진 중...");
        
    }

    @Override
    protected void prescribe(Patient Patient) {
        System.out.println("일반 처방이 완료되었습니다.");
        
    }
    
}

1-5. patient

public class Patient {
    private String name;   // 개인정보이므로 은닉한다.
    private int age;
    private String symptom;

    public Patient(String name, int age, String symptom) {
        this.name = name;
        this.age = age;
        this.symptom = symptom;
    }

    public String getName() { // 개인의 정보는 불변하므로 setter를 설정하지 않는다.
        return name;
    }
    public int getAge() {
        return age;
    }
    public String getSymptom() {
        return symptom;
    }

    

    public void showInfo(){ // 환자라는 객체는 적어도 자신을 설명할 수 있어야 한다.
        System.out.printf("[환자등록] %s (%d세), 증상: %s\n", name, age, symptom);
    }

}

1-6. HospitalDatabase (싱글턴 구조)

public class HospitalDatabase implements Reportable {
    private static HospitalDatabase instance = new HospitalDatabase(); // 프라이빗한 객체 선언 이 객체는 프라이빗해서 한번 허락을 받고 들어와야 한다.

    private HospitalDatabase(){} // 생성자의 접근 제어자를 막아버리면, 객체 생성을 통제할 수 있다. 생성자 = 객체 생성자 -> private은 클래스 내부에서만 접근할 수 있게 만드는 것으로 직접 하나의 클래스를 만든다.

    public static HospitalDatabase getInstance(){ // 유일한 객체를 생성하고 반환하는 책임까지 가진 특별한 메서드
        return instance;
    }

    @Override
    public void generateReport(Patient Patient) { // static이 붙지 않아서 이건 인스턴스 매서드다. 즉 객체를 통해서만 호출할 수 있다.
        System.out.printf("[저장] %s님의 진료 기록이 저장되었습니다.\n",Patient.getName());
    }

    
}
  • reportable 접근권한자
public interface Reportable {
    void generateReport(Patient Patient); // 리포트를 생성할 수 있는 능력 생성
} 

1-7. PaymentStrategy (전략 구조)

public class CreditcardPayment implements PaymentStrategy {
    @Override
    public void pay(int amount) {
        System.out.printf("[결제] 신용카드로 %d원 결제 완료\n", amount);
    }
}
  • card결제
public class CreditcardPayment implements PaymentStrategy {
    @Override
    public void pay(int amount) {
        System.out.printf("[결제] 신용카드로 %d원 결제 완료\n", amount);
    }
}
  • 모바일 결제
public class MobilePayment implements PaymentStrategy{
    @Override
    public void pay(int amount) {
        System.out.printf("[결제완료] 핸드폰으로 %d원 결제완료\n", amount);
    }
}
  • 현금결제
public class CashPayment implements PaymentStrategy {
    @Override
    public void pay(int amount) {
        System.out.printf("[결제완료] 현금금으로 %d원 결제완료\n", amount);
    }
}

1-8. 알림

public interface Notifiable{
    void notify(Patient patient, String message);
}
  • sms 알림
public class SmsNotifier implements Notifiable {

    @Override
    public void notify(Patient patient, String message) {
        System.out.printf("[알림] %s님에게 문자 발송: %s\n", patient.getName(), message);
        
    }
    
}
profile
학생

0개의 댓글