U E D R , A S I H C RSS

Java/문서/참조

  • 작성자 : 01 남상협
  • 찬조 : 99 류상민

이 문서를 작성하게된 계

채팅 UI를 짜려고 여러가지를 하다가 대화명을 입력하였을 경우에 그 대화명을 저장하려고 String 형태의 대화명을 전달인자로 사용하려고 하였는데 되지 않았다. 그래서 MSN을 통해서 상민이 형에게 그에 대해서 물어보았다. 상민이형이 MSN으로 몇십분에 걸쳐서 알려 주었다.(감사~) 이 문서에 나와 있는 내용에 대해서 아시는 분들도 있겠지만, 저와 같이 잘 모르는 분도 또한 있을거 같에 도움이 되를 바라면서 상민이 형이 알려준 내용을 간추려 보았다.

구체적인 내용

~cpp 
Java 에서는 new 와 delete 가 없지만 그 대안으로 참조형을 이용한다.
참조형은 C++에서 int &a와 같이 by-value가 아닌 by-reference로
값을 이용할 수 있는 형을 말한다.

자바는 본 자료형과 참조 자료형으로 크게 분류되며

본 자료형은 byte, short, int, long, double, char, boolean
참조형은 Class, Array, interface (예외 String은 본 자료형으로 취급한다.
String은 본 자료형만큼 자주 쓰 때문에 클래스 임에도 불구하고
본자료형으로 쓰인다.)

본 자료형은 스칼라(scalar) 형이다.
참조형은 백터(vector) 형.
간단히 비유하면 스칼라는 값, 백터는 화살표.

벡터는 call by-reference로 전달된다.
이런 reference자료형은 Class, 배열(Array) interface이며
call by-reference로 메소드나 전달인자로 넘어 간다.

 # 참고로 함수라는 말은 자바에서는 맞지 않는다.
   함수는 C에서만 존재 하는것이며 자바나 타 OOP언어에서는
   메소드라는 표현이 적절하다.
   메소드는 한 객체에 종속된 능이라는 부가적 의미를 가지고
   있 때문이다.

Class A
{
    public int a = 1;
    public void setA( int A ) { a = A; }
}

...
A _a;
A _A
_a.setA(3);
하면 될까? 안된다.(관련 내용은 제본책 3-3에 나와 있음)
안되는 이유는 아까 언급한 바와 같이 클래스는 vector값이 때문이다.

A _a;

에서 _a는 vector 값이다. 이 값은 한국말로 쉽게 표현하자면 방향값,화살표 이다.
그렇다면 현제 방향값인 _a는 무엇을 가리키고 있을까?
대답은 "현재는 아무것도 가리키고 있지 않다." 이다.
Java에서는 vector를 초화 시켜 주때문에, 객체가 없이 그냥 저렇게만 입력하면 null을 가리킨다.
그래서 위와 같은 경우

_a.setA(3);

을 호출하는 경우에는 NullPointerException이라면서 에러 객체를 발생시킨다.
그래서

A _a = new A();  //vector값 _a에게 가리킬 객체를 부여

이와같은 구문을 넣어서, 객체를 생성하고, _a에게 가리키게 하여야만 한다.
이와 대조적으로 스칼라(scalar) 값의 예를 들면

int a;
a = 1;

이건 성립한다. 이유는 int는 본 자료형으로서 스칼라 값이 때문이다.
스칼라(scalar) 역시 한국말로 표현하면, 양값(?) 이라고 해야하나, 방향성이 없는
그냥 양을 가리키는 용어이다.

이같은 스칼라 값들은 절대로 메소드에 reference형태의 전달인자로
넘겨줄 수 없다. 이것은 자바의 설계 이념이다.
자바에서는 스칼라 값 즉 본 자료형은 복사로(call by-value) 전달되고, return 값으로
해당 결과를 객체로 받는다. return 값이 스칼라 값이라면 어쩔 수 없다.
해당 설계이념은 Java Design Pattern 에 잘 나와 있다.

그리고 위에서 살포시 언급했던 String형은 본자료형과 비슷하게 스칼라형으로
취급하 때문에 call by-reference로 못넘긴다. 그래서 final로 선언할 수 있다.
(final이란 그냥 #define이라고 생각해도 무방하다. Java 컴파일러가 해당 final들을
실제 값으로 1:1 바꾸어 버리는 작업을 해버린다.)

위에서 언급했지만 다시 말하자면 String이 스칼라 취급을 받는 이유는 다음과 같다.
Java이전에 태어난 상업용 언어들은 대다수 char까지를 하나의 본 자료형으로 많이 차용했고
많은 언어에서 string형도 본자료로 쓸려는 노력을 많이 해두었다. (이유는 많이 쓰이 때문이다.)
인터넷이 보급되면서 java 설계자들은 String도 본자료형 취급을 해도 현재의
시스템들이 따라가 줄것이라 예상해서 그렇게 설계했다.

 # 참고 : 본 자료형들은 시스템내에서 마구 복사된다.
          그리고 만약 200KB 의 스트링 형에게 나중에 2byte 만을 할당하는 다음의 경우에도

	  String a = 200KB 자료
	  a = "a";(일단 개념적으로 이렇게 하겠음)

	  이렇게 되면 본 자료형으로 취급 받는 String은 통째로 200KB를 갈아 버린다.
	  문제는 200KB의 사소한  용향이 아닌 그게 2메가 짜리의 문서의 경우는 문제가 된다.
           여서의 의미는, String이 imutable하게 취급 받 때문에, 해당 객체의 저장소가 완전 초화 되고
           새로 할당 받는다는 의미이다. 물론 초화는 Garbage collector가 해주 때문에, 차후 메모리가
           부족할때 파괴 되어 진다.
           이게 심각한 이유는, 존 저장소를 그냥 유지한체로, String의 길이만 1로 하고, a[0]에 a문자열을
           집어 넣은 이후, 그대로 쓰면 되는데, String 객체는 새로 공간을 할당 받는다는 의미이다.

	  그래서 mutable한 String처리를 위해서 Java 1.2에서 등장한것이 StringBuffer 이고 이것은 vector값으로
           취급 받는다. 흔이 이 문제를 String의 mutable문제 라고 불리며 관련 자료에서 두 단어가 자주
	  등장한다. string is imutable. Stringbuffer is mutable
	  String은 한번 자료가 들어가면 바뀌지 않아서 주로 바뀌고 확장되는
	  문자열의자료의 경우 StringBuffer 를 사용하는 걸 권장한다.

           mutable한 객체의 구현을 위해 StringBuffer의 메소드를 보면, 일정 단위의 char저장 장소를 지정하여
           그 내부에서 문자열을 교체할수 있고, 그 저장 장소보다 더 큰 문자열이 입력이 된다면, 해당 문자열 길이의
           2배의 공간을 확보해 초화 한다..
Valid XHTML 1.0! Valid CSS! powered by MoniWiki
last modified 2021-02-07 05:23:33
Processing time 0.0122 sec