Open haji8-thehaji opened 3 weeks ago
Logger
와 StringBuilder
는 문자열 처리 및 로그 기록에 있어 각각의 역할과 특성이 다릅니다. 아래에서 두 가지의 차이점을 설명해 드릴게요.
StringBuilder:
Logger:
StringBuilder:
Logger:
StringBuilder:
Logger:
info()
, warning()
, severe()
, 등)를 제공합니다.StringBuilder 예제:
StringBuilder sb = new StringBuilder();
sb.append("User: ").append("Alice").append(" logged in.");
String logMessage = sb.toString();
System.out.println(logMessage);
Logger 예제:
import java.util.logging.Logger;
public class MyApp {
private static final Logger logger = Logger.getLogger(MyApp.class.getName());
public static void main(String[] args) {
logger.info("User logged in: Alice");
logger.warning("User attempted invalid login.");
}
}
따라서, 로그 메시지를 기록하는 경우에는 Logger
를 사용하는 것이 좋으며, 필요에 따라 StringBuilder
를 사용해 로그 메시지를 구성할 수 있습니다.
logger.info("User logged in: Alice"); 에다가 logger.info("User"+" logged in:"+" Alice"); 으로 설정하면 info안의 string 결합을 결국 string builder로 만들어야하지 않을까?
Java에서는 문자열 리터럴을 결합할 때 StringBuilder
를 사용하는 방식이 Java 5부터 도입되었습니다. Java 5에서는 컴파일러가 여러 문자열을 결합할 때 성능을 최적화하기 위해 StringBuilder
를 사용하도록 변경되었습니다.
이전 버전에서는 문자열 결합 시 매번 새로운 String
객체가 생성되어 메모리와 성능에 부담을 주었지만, Java 5부터는 StringBuilder
를 사용하여 효율성을 높였습니다.
따라서, Java 5 이상에서는 컴파일러가 문자열 리터럴을 +
연산자로 결합할 때 내부적으로 StringBuilder
를 사용하게 됩니다.
제어의 역전(Inversion of Control) 제어의 역전(IoC)란 모든 객체에 대한(생성, 라이프사이클 등) 제어권을 개발자가 아닌 IoC 컨테이너에게 넘긴 것을 말합니다.
의존성 주입(DI, Dependency Injection) 의존성 주입은 필요한 객체를 직접 생성하는 것이 아닌 외부로부터 객체를 받아서 사용하는 것입니다.이를 통해 객체간의 결합도를 줄이고 코드의 재사용성을 높일 수 있습니다.
VO와 BO, DAO, DTO에 대해 설명해주세요. DAO(Data Access Object) DB의 데이터에 접근을 위한 객체를 말합니다. (Repository 또는 Mapper에 해당) BO(Business Object) 여러 DAO를 활용해 비즈니스 로직을 처리하는 객체를 말합니다. (Service에 해당) DTO(Data Transfer Object) 각 계층간의 데이터 교환을 위한 객체를 말합니다. (여기서 말하는 계층은 Controller, View, Business Layer, Persistent Layer) VO (Value Object) 실제 데이터만을 저장하는 객체를 말합니다.
String, Stringbuffer, Stringbuilder 차이 String은 불변객체(immutable)한 객체입니다. 한번 생성된 객체의 값을 변결할 수 없으며 문자열을 조작할 때 마다 새로운 String객체가 생성되어 메모리를 차지하게 됩니다. 이로인해 연산이 많은 문자열에서는 작업 효율이 떨어질 수 있습니다. 그러나 불변성 덕분에 스레드 세이프하고, String객체를 자유롭게 공유할 수 있어 성능상 이점이 있을 수 있습니다. StringBuffer은 가변(mutable)객체입니다. 문자열 조작시에 기존 객체의 값을 변경합니다. 멀티 스레드환경에서 동기화를 지원하여 스레드 세이프합니다. 하지만 동기화로 인한 오버헤드가 있어 단일 스레드 환경에서는 성능이 저하될 수 있습니다. StringBuilder은 가변(mutable)객체입니다. 문자열 조작시에 기존 객체의 값을 변경합니다. 동기화를 지원하지 않아 스레드 세이프하지 않습니다. 하지만 동기화에 따른 오버헤드가 없기 때문에 단일 스레드 환경에서는 더 높은 성능을 제공합니다.
java의 접근제어자의 종류와 특징 public으로 선언된 클래스,메소드,변수는 다른 패키지의 모든 클래스에서 접근할 수 있습니다. protected으로 선언된 변수와 메소드는 같은 패키지 내의 다른 클래스와, 해당 클래스를 상속받은 자식클래스에서도 접근할 수 있습니다. 일반적으로 오버라이드 할 수 있는 메서드나 변수를 선언할 때 사용됩니다. default 접근 제어자를 명시하지 않는경우로 클래스, 멤버변수 메서드는 같은 패키지 내의 클래스에서만 접근할 수 있습니다. private으로 선언된 멤버변수와 메서드는 오직 선언된 클래스 내부에서만 접근할 수 있습니다. 객체의 내부 상태를 캡슐화하고 외부로부터 보호할 때 사용됩니다.
클래스, 객체, 인스턴스의 차이 클래스 클래스는 객체지향 프로그래밍에서 특정 개체의 속성과 행위를 정의하는 설계도라고 할 수 있습니다. 클래스는 멤버변수와 메서드로 구성되며 멤버변수는 해당 클래스의 객체들이 가질 수 있는 상태를 정의하고, 메서드는 객체들이 수행할 수 있는 행위를 정의합니다. 객체는 클래스에 의해 정의된 설계도를 따라 만들어진 실체로, 객체는 클래스의 인스턴스입니다. 객체는 메모리에 할당되며 각 객체는 고유한 상태를 가지고 클래스에 정의된 행위(메소드)를 수행할 수 있습니다. 인스턴스는 클래스의 객체를 의미합니다. 클래스를 통해 객체를 생성할 때마다 새로운 신스턴스가 생성되는 것입니다. 인스턴스는 클래스에 정의된 속성과 행위를 가진 객체로 각 인스턴스는 고유한 상태를 가집니다. 객체가 특정 클래스의 인스턴스라는 것은 해당 객체가 해당 클래스의 설계도에 따라 생성되었다는 것을 의미합니다. 즉, 클래스는 객체의 설계도이며, 객체는 클래스에 정의된 속성과 행위를 가진 실체입니다. 인스턴스는 클래스의 객체를 나타내는 용어로 사용되며 클래스로 부터 생성된 객체를 의미합니다.
Call by Reference와 Call by Value의 차이 Call by Value방식은 함수에 인자를 전달할 때 인자값을 복사하여 전달하는 방식입니다. 이 방식에서는 원본 데이터와 전달된 복사본이 서로 다른 메모리 주소를 가지기 때문에, 함수 내에서 인자의 값을 변경해도 원본 데이터에는 영향을 미치지 않습니다. C, C++, Java, Python 등이 call by value 방식을 사용합니다. Call by Reference방식은 함수에 인자를 전달할 때 인자의 메모리 주소를 전달하는 방식입니다. 함수 호출시에 인자로 전달되는 변수의 레퍼런스를 전달하며 해당 주소를 통해 원본 데이터를 직접 수정할 수 있습니다. C++, Swift, PHP 등이 call by reference 방식을 지원합니다.
꼬리) java의 기본 타입은 call by value고 참조타입은 call by reference다? 놉 java는 call by value로 작동합니다. java의 참조변수에는 원본 객체에 대한 참조를 값으로 복사하여 가지고 있습니다. 즉 변수가 가지는 값이 레퍼런스이므로 인자로 넘길 때 call by value에 의해 변수가 가지고 있는 레버런스가 복사되어 전달되는것 입니다. 함수 내에서 객체의 속성을 변경하게 되면 원래 객체에 영항을 줄 수 있지만 함수 내에서 전달된 참조변수 자체를 변경하면 호출자의 원래 참조에는 영향을 주지 않습니다.
Java 언어의 장단점 장점:
OOP의 4가지 특징 추상화(Abstraction), 캡슐화(Encapsulation), 상속(Inheritance), 다형성(Polymorphism)
추상화란 특정 개념이나 개체를 보았을 때 특정 관점에서 관심있거나 중요한 부분만 추려내는 작업을 의미합니다. 즉, OOP에서 중요한 정보만 객체의 인터페이스로써 표시하고 구현 세부 정보를 숨길 수 있는 OOP의 매우 중요한 기능입니다. 캡슐화란 데이터와 프로세스를 하나의 객체에 위치하도록 만드는 것을 말한다. 이를 통해 객체는 자율적으로 다른 객체들과 협력할 수 있는 객체가 되며 자연스레 시스템의 결합도는 떨어지고 응집도는 올라가게 된다. 이의 결과로서 시스템 전체는 유지보수하기 쉬워지고 추후 변경에 유연하게 대처할 수 있다. 상속이란 부모 객체의 특징을 그대로 물려받는 것을 의미하고, 자바에서는 인터페이스 상속과 클래스 상속으로 나뉜다. 이를 통해 모듈의 재사용성이 높아지고, 다형성을 구현할 수 있다. 하지만 무분별한 상속의 남용은 시스템의 결합도를 올려 추후 변경에 유연하게 대응하지 못하기 때문에 자제해야한다. 다형성이란 같은 요청으로부터 응답이 객체의 타입에 따라 다르게 나타나는 것을 의미합니다. 이를 통해 객체지향은 더 유연한 설계를 가질 수 있습니다.
OOP의 5대 원칙 (SOLID) S: 단일 책임 원칙(SRP, Single Responsibility Principle) 단일 책임 원칙이란 하나의 클래스가 변경되는 이유는 하나뿐이어야한다. -> 하나의 클래스는 하나의 원칙만 가져야한다. 하나의 책임이란것은 모호합니다. 하나의 역할만 가져야 한다기보다 문맥과 상황에 따라 잘 설계해야 합니다. ex) Controller에서 비즈니스 로직을 처리한다면 클라이언트의 요청과 응답을 처리하는 역할과 비즈니스로직 처리역할 둘 다 하게됨으로 단일책임원칙에 위배됩니다. Controller는 요청과 응답을 Service는 비즈니스로직을 처리하는것이 단일책임 원칙을 지키는 것 입니다. O: 개방-폐쇄 원칙(OCP, Open Closed Principle) 자신의 확장에는 열려있고 주변의 변화에는 닫혀있어야 한다. 기존의 코드를 변경하지 않고 새로운 기능을 추가할 수 있어야한다. ex) 가장 좋은 예는 JDBC 인터페이스라고 할 수 있습니다. JDBC인터페이스로 표준화 하지 않았다면 DB를 바꿀 때 마다 각자 제공하는 API에 따라 코드를 수정했어야 했을 것 입니다. 하지만 JDBC 인터페이스를 제공함으로써 Connection을 설정하는 부분만 해당 드라이버로 수정해 주면 DB를 교체할 수 있습니다. L: 리스코프 치환 원칙(LSP, Liskov Substitution Principle) 하위클래스는 상위클래스의 역할을 하는데 문제가 없어야 한다. 자식클래스는 부모클래스의 역할을 모두 할 수 있어야한다. I: 인터페이스 분리 원칙(ISP, Interface Segregation Principle) 하나의 일반적인 인터페이스보다는 여러개의 구체적인(클라이언트에 특화된) 인터페이스를 사용해야한다. D: 의존 역전 원칙(DIP, Dependency Inversion Principle) 의존관계를 맺을 때 변화하기 쉬운것보다 거의 변화하지 않는것에 의존해야한다. 구체화에 의존하지 말고 추상화에 의존해야한다. -> 구현클래스에 의존하지 말고 인터페이스에 의존해야한다.
==와 equals의 차이점은 무엇입니까? ==는 두 객체의 참조(메모리 주소)를 비교하는 연산자입니다. 두 객체의 참조가 동일한 경우에만 true를 반환합니다. equals() 메서드는 객체들 간의 내용적인 동등성을 비교하는 메서드입니다. 즉, 두 객체의 값이 동일한 경우에 true를 반환합니다. equals() 메서드는 객체의 클래스에 따라 재정의할 수 있습니다
스레드와 프로세스의 차이점은 무엇입니까? 스레드는 프로세스 내에서 실행되는 실행 단위입니다. 한 프로세스는 여러 개의 스레드를 가질 수 있으며, 스레드는 공유 자원에 접근할 수 있습니다. 프로세스는 운영 체제에서 실행 중인 프로그램 인스턴스를 나타냅니다. 각 프로세스는 독립된 메모리 공간과 자원을 가지며, 다른 프로세스와는 분리되어 실행됩니다.
깊은 복사와 얕은 복사의 차이점은 무엇인가요? 얕은 복사(Shallow Copy): 얕은 복사는 객체의 필드를 복사할 때, 필드의 참조를 그대로 복사합니다. 따라서 원본 객체와 복사본은 같은 참조를 공유하게 되어, 한 객체의 상태 변경이 다른 객체에 영향을 줄 수 있습니다. 깊은 복사(Deep Copy): 깊은 복사는 객체의 필드를 복사할 때, 필드의 새로운 인스턴스를 생성하여 복사합니다. 따라서 원본 객체와 복사본은 완전히 독립적인 객체가 되어, 한 객체의 상태 변경이 다른 객체에 영향을 주지 않습니다. 깊은 복사는 객체 그래프를 재귀적으로 탐색하여 모든 필드를 복사하는 것을 의미합니다.
세션과 쿠키의 차이점은 무엇인가요? 세션과 쿠키는 웹 애플리케이션에서 사용되는 상태 관리 기술입니다. 쿠키는 클라이언트 측에 저장되는 작은 데이터 조각이며, 클라이언트의 요청과 응답 헤더에 포함됩니다. 주로 클라이언트 식별과 상태관리에 사용됩니다. 쿠키는 클라이언트 측에서 관리되며 만료 날짜 및 시간을 설정할 수 있습니다. 세션은 서버 측에 상태 정보를 저장하는 데 사용되는 객체입니다. 각 클라이언트에 대해 고유한 세션 ID가 생성되며, 이를 통해 클라이언트와 서버 간의 상태 정보를 유지합니다. 세션은 일정 시간 동안 유지되며 서버 측에서 관리됩니다.
SQL 인젝션을 피하는 방법은 무엇인가요?SQL 인젝션은 악의적인 사용자가 입력 데이터를 조작하여 데이터베이스에 악의적인 쿼리를 주입하는 공격입니다. 이를 피하기 위해 다음과 같은 조치를 취할 수 있습니다
Prepared Statement 또는 Parameterized Query를 사용하여 동적 쿼리 생성을 피합니다. 입력 데이터의 유효성을 검증하고, 필요한 경우 데이터 필터링과 이스케이프 처리를 수행합니다. 데이터베이스 계정에는 최소한의 권한만 부여하여 보안을 강화합니다. ORM(Object-Relational Mapping) 프레임워크를 사용하여 SQL 쿼리 생성과 관리를 자동화합니다.