package CHAPTER05;

class User {
    private String name;
    private String email;
    private static int userCount = 0; // 전체 사용자 수

    // 기본 생성자
    public User() {
        this("Unknown", "no-email");
    }

    // 생성자 오버로딩
    public User(String name) {
        this(name, "no-email");
    }

    public User(String name, String email) {
        this.name = name;
        this.email = email;
        userCount++; // 사용자 수 증가
    }

    // Getter & Setter (캡슐화 적용)
    public void setEmail(String email) {
    	 this.email = email;
    }
    
    public String getName() {
        return name;
    }

    public String getEmail() {
        return email;
    }

    public static int getUserCount() {
        return userCount;
    }

    // 객체 삭제 시 GC 동작 확인 (가비지 컬렉션)   
    protected void finalize() {
        userCount--; // 사용자 수 감소
        System.out.println("GC 실행 요청: 객체가 곧 삭제됩니다.");
    }

    // 사용자 정보 출력
    public void displayUserInfo() {
        System.out.println("이름: " + name + ", 이메일: " + email);
    }
}

class Product {
    private String productName;
    private int price;
    private static int productCount = 0; // 전체 상품 수

    // 기본 생성자
    public Product() {
        this("Unknown Product", 0);
    }

    // 생성자 오버로딩
    public Product(String productName) {
        this(productName, 0);
    }

    public Product(String productName, int price) {
        this.productName = productName;
        this.price = price;
        productCount++; // 상품 수 증가
    }

    // Getter & Setter (캡슐화 적용)
    public String getProductName() {
        return productName;
    }

    public int getPrice() {
        return price;
    }

    public static int getProductCount() {
        return productCount;
    }

    // 객체 삭제 시 GC 동작 확인 (가비지 컬렉션)    
    protected void finalize() {
        productCount--; // 상품 수 감소
        System.out.println("GC 실행 요청: 객체가 곧 삭제됩니다.");
    }

    // 상품 정보 출력
    public void displayProductInfo() {
        System.out.println("상품명: " + productName + ", 가격: " + price + "원");
    }
}

public class REAL_OnlineSystem {
    public static void main(String[] args) {
        // 1. 사용자 및 상품 생성 (생성자 오버로딩 적용)
        User user1 = new User("Alice", "alice@example.com");
        User user2 = new User("Bob", "bob@example.com");
        
        user1.setEmail("alice@example.com");

        Product product1 = new Product("노트북", 1500000);
        Product product2 = new Product("스마트폰", 1000000);

        // 2. 사용자 및 상품 정보 출력
        System.out.println("[사용자 1 정보]");
        user1.displayUserInfo();
        System.out.println("\n[사용자 2 정보]");
        user2.displayUserInfo();

        System.out.println("\n[상품 1 정보]");
        product1.displayProductInfo();
        System.out.println("\n[상품 2 정보]");
        product2.displayProductInfo();

        // 3. 전체 사용자 및 상품 수 출력 (static 활용)
        System.out.println("\n전체 사용자 수: " + User.getUserCount());
        System.out.println("전체 상품 수: " + Product.getProductCount());

        // 4. 객체 삭제 (가비지 컬렉션 테스트)
        System.out.println("\n사용자 Bob 삭제...");
        user2 = null; // 객체 삭제 준비

        System.out.println("상품 스마트폰 삭제...");
        product2 = null; // 객체 삭제 준비

        System.gc(); // 가비지 컬렉션 강제 실행 요청

        // 5. 사용자 및 상품 수 재확인
        System.out.println("\n현재 사용자 수: " + User.getUserCount());
        System.out.println("현재 상품 수: " + Product.getProductCount());
    }
}
