관리 메뉴

Heizelnut의 IT이야기

Bundle, Serializable, Parcelable 본문

Android/개발관련

Bundle, Serializable, Parcelable

Heizelnut 2012.10.25 21:03
크리에이티브 커먼즈 라이선스
Creative Commons License

Bundle

문자열로 된 키와 여러가지의 타입의 값을 저장 하는 일종의 Map 클래스이다.

Android에서 Activity간에 데이터를 주고 받을 때 Bundle 클래스를 사용하여 여러 가지의 데이터를 전송한다.

기본타입인 int, double, long, String 부터 FloatArray, StringArrayList Serializable, Parcelable 구현한 객체를 전송한다.

http://developer.android.com/reference/android/os/Bundle.html

링크를 통해 API를 확인해보면 다양한 put,get 메소드가 존재하는지 확인 가능하다.

간단한 타입의 경우는 다들 금방 사용해보시면 아실테고 좀 익숙하지 않는 Serializable, Parcelable 인터페이스에 대해 알아보자.


Serializable 


- 객체를 일차원의 데이터로 저장하는 기능

- 마샬과 언마샬을 사용한다.

- 마샬링 : 객체를 byte stream으로 변환

- 언마샬링 : byte stream을 객체로 변환

- 객체를 직렬화 시켜서 객체 단위로 데이터를 주고 받을 수 있다. 

- java.io.Serializable 인터페이스만 명시해주면 해당 클래스는 직렬화 가능한 클래스가 된다.

- Android에서는 Bundle을 사용하여 Activity간 데이터를 주고 받는데 Bundle의 메소드 중


다음과 같은 메소드를 제공해줍니다.

void putSerializable(String key, Serializable value) 

Serializable getSerializable(String key)



<소스1>

 public class Dog implements Serializable {


    private String name;

    private int age;

    private int type;

    

    public Dog(String name, int age){

        this.name = name;

        this.age = age;

    }


    public String getName() {

        return name;

    }


    public void setName(String name) {

        this.name = name;

    }


    public int getAge() {

        return age;

    }


    public void setAge(int age) {

        this.age = age;

    }


    public int getType() {

        return type;

    }


    public void setType(int type) {

        this.type = type;

    }

}


Bundle에서 사용 할 경우

------------------------------------------------

Dog dog = new Dog("Dog1", 10);

extras.putSerializable("key1", dog);

------------------------------------------------

Bundle extras = intent.getExtras();

Dog dog = (Dog)extras.getSerializable("key1");




Parcelable

- Parcel : 소포, 꾸러미라는 뜻,  객체를 전달 가능한 형태로 포장하는 것

- 원래 프로세스간의 통신을 위한 메시지 저장 장치 인데 번들이 꾸러미 입출력 기능을 제공하므로 같은 프로세스의 세션간 데이터 저장 및 복구에도 사용 가능하다.

- Serializable 인터페이스와 동일하게 Parcelable 인터페이스를 구현하면 객체 단위로 Activity간에 전달 할 수 있다.


다음과 같은 메소드를 제공한다.

void putParcelable(String key, Parcelable value)

void putParcelableArray(String key, Parcelable[] value)

void putParcelableArrayList(String key, ArrayList<? extends Parcelable> value)


T getParcelable(String key)

Parcelable[] getParcelableArray(String key)

ArrayList<T> getParcelableArrayList(String key)


- Parcelable 인터페이스를 구현 할 때 다음 두 개의 메소드를 구현 해야 한다.

int  describeContents()

void writeToParcel(Parcel dest, int flags)


writeToParcel() 메소드를 통해 객체의 멤버필드 값을 Parcel 객체로 보낸다.


그리고 Parcelable.CREATOR라는  정적 인터페이스를 제공하는데 Parcel 객체에 저장된 각각의 멤버필드의 값을

Parcel로 부터 읽어 들여 Parcelable를 구현한 객체를 생성한다.


다음 두 메소드를 오버라이드 해야 한다.

T createFromParcel(Parcel source)

Parcel객체로부터 저장된 Parcelable 객체의 정보를 읽어들여 객체를 다시 생성한다.


T[] newArray(int size)

Parcelable 객체 수만큼 배열을 생성한 후 루프를 돌며 꾸러미에서 객체를 하나씩 꺼내 배열에 집어 넣는다.


정리하면

(하단 소스 참고)Parelable인터페이스를 구현한 City라는 클래스가 있다면

writeToParcel()를 통해 Parcel 객체에 City의 멤버필드 값들이 write되고


Parcelable.CREATOR 인터페이스를 통해 Parcel 객체에 저장된 City의 멤버필드 값들을

read해서 새로운 City 객체를 만든다.


그리고 newArray()를 통해 City가 ArrayList 또는 Array 형태로 저장된 경우

해당 개수 만큼 newArray()를 통해 City객체를 만들어 배열로 리턴해준다.


개발자는 다음과 같이 CREATOR 인터페이스와 오버라이드할 메소드를 구현한 다음

put,get메소드를 통해 Parcelable 객체를 사용하면 된다.


<소스2>

 public class City implements Parcelable {

    

    private String name;

    private int number;

    

    public String getName() {

        return name;

    }


    public void setName(String name) {

        this.name = name;

    }


    public int getNumber() {

        return number;

    }


    public void setNumber(int number) {

        this.number = number;

    }

    

    public City(String name, int number){

        this.name = name;

        this.number = number;

    }

    

    @Override

    public int describeContents() {

        return 0;

    }


    @Override

    public void writeToParcel(Parcel dest, int flags) {

        dest.writeString(name);

        dest.writeInt(number);

    }

    

    public static final Parcelable.Creator<City> CREATOR = new Creator<City>(){

        public City createFromParcel(Parcel source){

            String name = source.readString();

            int number = source.readInt();

            return new City(name, number);

        }

        

        public City[] newArray(int size){

            return new City[size];

        }

    };

}


<Bundle에서 사용하는 경우>

------------------------------------------------

ArrayList<City> cityList = new ArrayList<City>();

cityList.add(new City("Seoul",1231));

cityList.add(new City("Tokyo",1232));

cityList.add(new City("New York", 1233));

extras.putParcelableArrayList("key2", cityList);

                                

extras.putParcelable("key3", new City("LA", 1235));

                                 

City[] cityArray = new City[3];

cityArray[0] = new City("Washington",2345);

cityArray[1] = new City("Kobe",32136);

cityArray[2] = new City("Osaka", 7671);

extras.putParcelableArray("key4", cityArray);


------------------------------------------------

ArrayList<City> cityList = extras.getParcelableArrayList("key2");


City city1 = extras.getParcelable("key3");


Parcelable[] cities = extras.getParcelableArray("key4");

for(Parcelable city : cities){

      City c = (City)city;

      android.util.Log.i("Activity2", "key4 = " + c.getName());

}




마무리


Bundle, Serializable, Parcelable에 대해 조금이나마 이해하는데 도움이 되었으면 합니다.


출처 : http://blog.daum.net/mellowwind

신고
2 Comments
댓글쓰기 폼