나의 즐겨찾기 | 블로그홈 | 바로가기 바로가기 | 로그인
崇本息末
블로그  |  사진갤러리  |  동영상갤러리 방명록  |   즐겨찾기 추가


아래는 번역하다 만 상태입니다.
---



J2SE 1.5 뭐가 달라졌나?

Based on Joshua Bloch's on-line talk

1. J2SE 1.5(타이거-호랑이) 베타버전이 2004년 초 공개됐다. 이 릴리즈는 품질, 모니터링과 관리 편의, 성능 향상과 확장성 그리고 개발과 데스크탑 용도 사용 편의라는 몇몇 핵심 주제에 포커스를 맞추고 있다.

2. Joshua Bloch 가 쓴 타이거에 관한 시가 아래에 인용되어 있다.

3. 제너릭(Generics) - 컴파일 할 때 컬렉션에 자료형을 안전하게 사용할 수 있도록 보장해주며, 짜증나는 캐스팅을 없애준다.


시 인용:
가장 짜증나는 캐스팅에게
우리는 드디어 작별을 고하네
제너릭의 불타오르는 창끝에
캐스팅은 사라져가네.

String 객체를 위해 java.util.List를 사용해서 값을 가져올 때마다 String 으로 캐스팅을 해야했다.
List names = new ArrayList();
...
String name = (String)names.get(idx);

제너릭을 이용하면, List<String>으로 선언하여 컴파일러가 대신 형을 검사하게 한다. 자료형을 안전하게 사용할 수 있고, 리스트에서 값을 가져올 때 캐스팅도 불필요 하다. 그러므로 위 코드는 다음과 같이 쓸 수 있다.
List<String> names = new ArrayList<String>();
...
String name = names.get(idx);

주의: J2SE 컴파일러는 자동으로 자료형을 검사해 줄것이다. ClassCastException은 발생하지 않을 것이고, 컬렉션의 요소가 필요할 때 캐스팅할 필요도 없다.

예제 하나 더 : 4문자 단어 없애기

현재의 코드:
static void expurgate(Collection c) {
    for (Iterator i = c.iterator(); i.hasNext(); ) {
        String s = (String) i.next();
        if(s.length() == 4)
            i.remove();
    }
}

제너릭을 이용한 코드:
static void expurgate(Collection<String> c) {
    for (Iterator<String> i = c.iterator(); i.hasNext(); )
        if (i.next().length() == 4)
            i.remove();
}

자바의 제너릭은 형을 철저하게 검사하여, 오직 지정된 형 파라미터의 메소드만을 호출 할 수 있다.
제너릭 메소드 선언의 예를 보이면:
    ....
    void f(T t) { 
       t.whatever(); 
    }

그리고 이 메소드의 형 파라미터를 Foo의 서브클래스나 서브인터페이스로 지정했다.
만약 Foo가 whtaever() 메소드를 가지고 있다면, whtever() 메소드를 사용할 수 있고, 정적으로 형 검사를 하게 되며 안전한 형이 된다.

형 파라미터 여러개 주기:
<T extends Interface1 & Interface2>

서로 다른 형 파라미터를 지정할 때 쉼표(,) 대신에 & 가 쓰였음을 주의하라.

4. 발전된 for 반복문 - 짜증나고 오류나기 쉬운 이터레이터를 없애준다.


시 인용:
이터레이터가 쓰일 때
그들은 때때로 올가미 처럼 우리를 옥죄었네
발전된 for 문이 한줄기 서광이되어
이터레이터를 궁지에 빠뜨렸네.

발전된 for 반복문("foreach"로 알려진)이 이터레이터나 인덱싱 변수 없이 컬렉션과 배열을 순회 할 수 있게 해준다.

현재의 코드:
void cancelAll(Collection c) { 
    for (Iterator i = c.iterator(); i.hasNext(); ) {
        TimerTask tt = (TimerTask) i.next();
        tt.cancel();
    }
}

J2SE 1.5의 코드:
void cancelAll(Collection c) {
    for (Object o : c)
        ((TimerTask)o).close();
}

콜론( : )은 "in."이라고 읽는다.

혹은 두가지 새로운 기능을 이용해:
void cancelAll(Collection<TimerTask> c) {
    for (TimerTask task : c)
        task.cancel();
}

5. 오토박싱/언박싱 - 원시 형(int 같은)과 래퍼 객체(Integer 같은)간의 짜증나는 수동 변환을 없애준다.

예를 들면,

시 인용:
컬렉션에서 int 를 빼낼 때 마다
래퍼 클래스는 우릴 슬프게 만들었네.
호랑이가 나타나면 우리는 눈물을 멈추리
우리는 이삭일때 상자에 넣으리(We'll autobox them in the ears) // 해석 못하겠슴.. ^^

J2SE 1.5 코드:
public class Freq {
    public static void main(String args[]) {
       Map<String, Integer> m = new TreeMap<String, Integer>();
       for (String word : args)
           m.put(word, m.get(word) + 1);
       System.out.println(m);
    }
}

현재의 코드:
public class Freq {
    private static final Integer ONE = new Integer(1);

    public static void main(String args[]) {
        Map m = new TreeMap();

        for (int i=0; i            <args.length; i++) {
            Integer freq = (Integer) m.get(args[i]);
            m.put(args[i], (freq==null ? ONE             :
                  new Integer(freq.intValue() + 1)));
        }
        System.out.println(m);
    }
}

6. 형이 안전한(Typesafe) enum - 이것은 말 많고 에러 나기 쉬운 점들이 없이 Typesafe Enum 의 잘 잘려진 장점들을 제공해 준다.


주의 : enum 은 키워드이므로, 옛날 자바 코드에서 이것을 형의 이름(변수/클래스/메소드 이름 등)으로 사용했다면, -source 1.5 를 사용하기 위해 그것들을 모두 수정해야 한다.

시 인용:

정수 enum 은 곧 사라지리
너무 길었던 우리의 적처럼
형이 안전한 enum의 강력한 힘은
우리의 적을 무력화 시키네.

public enum Coin {
    penny(1), nickel(5), dime(10), quarter(25);

    Coin(int value) { this.value = value; }

    private final int value;

    public int value() { return value; }
}

public class CoinTest {
    public static void main(String[] args) {
        for (Coin c : Coin.VALUES)
            System.out.println(c + ":   \t"
                  + c.value() +"� \t" + color(c));
    }
    private enum CoinColor { copper, nickel, silver }
    private static CoinColor color(Coin c) {
        switch(c) {
          case Coin.penny:   return CoinColor.copper;
          case Coin.nickel:  return CoinColor.nickel;
          case Coin.dime:
          case Coin.quarter: return CoinColor.silver;
          default: throw new AssertionError("Unknown coin: " + c);
        }
    }
}

See how the constant declarations invoke a constructor, passing in an int that represents the value in cents? And see how the value is stored in a private field with a public accessor? See how we declare another enum for the colors? See how we can switch on enum constants? This is very useful when you want to "add a method" to an enum class, but you can't modify the class for whatever reason.

Actually, the new enums are more than mere structs in other languages. If you don't add any methods or fields, they're just "rich" typesafe enum constants. If you add methods or fields in, they are just full-fledged objects.

Return to top

7. Static import - Static import 는 Constant Interface 안티패턴의 단점을 피해, 클래스이름없이 정적 멤버를 사용할 수 있게 해준다.


예를 들면:

시 인용:

And from the constant interface
we shall inherit no disgrace
With static import at our side,
our joy will be unqualified

public interface Promotion {
  public static final double MANAGER_RATE   = 0.59;
  public static final double SUPERVISER_RATE   = 0.35;
}

Promotion 인터페이스를 사용하려할 때, 지금까지는 인터페이스를 구현(implement)해야 했다. 하지만 J2SE 1.5 에서는 다음과 같이 import 해도 된다.

import static whatever.sub.Promotion;

class Test {
    public static void main(String[] args) {
        double extra_salary = MANAGER_RATE * current_salary;
        ...
    }
}

주의: Promotion은 클래스이어도 된다. 상수 클래스 디자인에 유용하다.

8. Metadata - lets you avoid writing boilerplate code, by enabling tools to generate it from annotations in the source code. This leads to a "declarative" programming style where the programmer says what should be done and tools emit the code to do it. For example, define attributions and build tool to do it.


시 인용:

And as for noble metadata
I'll have to sing its praises later
Its uses are so numerous
To give their due, I'd miss the bus

public class Test { 
    @Somewhere public void someMethod() {
        ...
    }
    
}


The code will be generated by the @Somewhere annotation.

It is also called "Program Annotation."

Note that the metadata will not introduce any new language keyword. It makes clever use of existing "punctuation." To declare an annotation type:
{{{ public @interface Foo { ... } }}}

Here "@interface" means "annotation-type" (get it? a-t -> at -> @). Also, it looks like a javadoc tag.

To annotate:
@Copyright("Acme Inc") public static final int baz(...) {
    ...
} 

9. Java 변수 인자들이 객체의 배열이다. 컴파일러는 인자 메소드에 전달된 목록에 기반하여 배열로 합친다.


public void aMethod(String... args) {
    for(String s : args) {
        System.out.println(s);
    }
}

aMethod 는 다음과 같은 형태로 호출된다 :
aMethod("here","we","go"); //3 argument list
aMethod("to","be","or","not","to","be"); //6 argument list

컴파일러는 인자 목록을 자동으로 다음과 같이 만든다 :
aMethod(new String[] {"here","we","go"});
aMethod(new String[] {"to","be","or","not","to","be"});

10. The reflection APIs are being extended to handle enums,generics and annotations.

11. J2SE 1.5 introduces revisions to the core XML platform, including XML 1.1, SAX 2.0 and DOM Level 3.

12. 32-bit surrogate character support will be carefully added to the platform so the Java "char" will still remain at 16 bits.

13. java.lang.StringBuilder is added in j2SE 1.5. It is a unsynchronized version of java.lang.StringBuffer. Because StringBuffer is a fully syncronized, it makes String concatenation fairly slow. StringBuilder will be used by the compiler to compile string concatenation expressions, and this should significantly improve performance for some applications.

14. Two new look and feels: an XP look and feel and a Linus GTK 2.0 look and feel. The default look and feel (metal) has been updated.

15. Program startup is improved.

16. X.class will be of type Class.

17. Easy of use functionality to JTable, etc.

18. Many new APIs, like java.util.concurrent, which does for concurrency (to prevent deadlock) what the Java Collections Framework did for data structures.

19. All of the "wrapper" classes like weak references and thread locals will be retrofitted to use generics. So will some APIs that return specified generics (for example, List).

20. Tuples, which is a way to handle multiple return types, will be considered in the future version.

21. const keyword will not be supported in J2SE 1.5 or later. It has been rated as a conserved keyword since J2SE 1.0. Use final instead.

22. java.util.Data will keep same. It has a small change, It will implement Comparable<Date> instead of just Comparable. The Date class has a problem of mutation. When to change it? not know yet.

23. delegates, defined in J++ and C#, will not be included in J2SE 1.5.

24. Operator overloading will not be included in J2SE 1.5.

25.

26. More to come. Stay tuned.



Joshua Bloch의 시

Tiger, Tiger Burning Bright
Like a geek who works all night
What new-fangled bit or byte
Could ease the hacker's weary plight?

To the most despised cast
We'll bid a fond farewell at last
With generics' burning spear
The need for cast will disappear

While Iterators have their uses
They sometimes strangle us like nooses
With enhanced-for's deadly ray
Iterator's kept at bay

When from collections ints are drawn
Wrapper classes make us mourn
When Tiger comes, we'll shed no tears
We'll autobox them in the ears

The int-enum will soon be gone
like a foe we've known too long
With typesafe-enum's mighty power
Our foe will bother us no more

And from the constant interface
we shall inherit no disgrace
With static import at our side,
our joy will be unqualified

And as for noble metadata
I'll have to sing its praises later
Its uses are so numerous
To give their due, I'd miss the bus

댓글쓰기

댓글쓰기 입력폼

포스트 목록 닫기

목록보기
 
전체 글보기(245)
!리눅스
!프로그래밍
!XML & WebServices
!데이터베이스
!컴퓨터 팁
!나의 프로그램들
!테마 게시판
!책갈피
!공지사항
오늘 전체
방문자 330 286534
구독자 0 48
댓글 0 181
참조글 0 18
HanRSS 로 구독하기Fish 로 구독하기
개설일 : 2004/02/24