Читання та запис java.util.Date з класу Parcelable


79

Я працюю в класі Parcelable. Як я можу читати та писати java.util.Dateоб'єкти до цього класу та з нього?

Відповіді:


186

Використовуйте writeSerializable там, де Date можна серіалізувати. ( Але це не гарна ідея. Дивіться нижче інший кращий спосіб )

@Override
public void writeToParcel(Parcel out, int flags) {
   // Write object
   out.writeSerializable(date_object);

}

private void readFromParcel(Parcel in) {
   // Read object
    date_object = (java.util.Date) in.readSerializable();

}

Але операції серіалізації споживають багато продуктивності. Як це подолати?

Тож краще використовувати перетворення дати в Long під час запису, а читання Long і перехід до конструктора Date, щоб отримати Date. Дивіться нижче код

   @Override
    public void writeToParcel(Parcel out, int flags) {
       // Write long value of Date
       out.writeLong(date_object.getTime());

    }

    private void readFromParcel(Parcel in) {
       // Read Long value and convert to date
        date_object = new Date(in.readLong());

    }

3
Але операції серіалізації споживають багато продуктивності. Як це подолати?
Месут

1
Ви дійсно повинні робити це, використовуючи longs, оскільки Serializable не підходить для продуктивності, що помітно на старих пристроях. Можливо, ви також захочете поглянути на Joda, оскільки вона містить безліч корисних інструментів і має об’єкт DateTime, який я часто вважаю більш корисним.
Грем Сміт

Зараз нормально Я вважаю за краще використовувати long замість серіалізації.
Месут

@Mesut Чудово! конг ви отримали своє рішення.
Панкадж Кумар

1
@JockyDoe Це не буде. Послідовність полів під час парцеляції та розпакування. Тож перевірте, чи використовуєте ви однакове замовлення для обох полів.
Панкадж Кумар,

18

У Kotlin ми можемо створити розширення для посилки - найпростіше рішення.

fun Parcel.writeDate(date: Date?) {
    writeLong(date?.time ?: -1)
}

fun Parcel.readDate(): Date? {
    val long = readLong()
    return if (long != -1L) Date(long) else null
}

І використовувати його

parcel.writeDate(date)
parcel.readDate()

14

Використовуйте date.getTime () для отримання формату Long:

public class MiClass implements Parcelable {
    Date date;

    public MiClass(Date date) {
        this.date = date;
    }

    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(Parcel dest, int flags) {
        dest.writeLong(date != null ? date.getTime() : -1);
    }

    protected MiClass(Parcel in) {
        long tmpDate = in.readLong();
        this.date = tmpDate == -1 ? null : new Date(tmpDate);
    }

    public static final Parcelable.Creator<MiClass> CREATOR = new Parcelable.Creator<MiClass>() {
        public MiClass createFromParcel(Parcel source) {
            return new MiClass(source);
        }

        public MiClass[] newArray(int size) {
            return new MiClass[size];
        }
    };
}

Це хороше рішення, але воно не працюватиме належним чином для дат до 1/1/1970. -1L насправді є дійсним значенням, яке представляє одну мілісекунду до 1/1/1970. Тому я б скоріше використовував значення типу Long.MIN_VALUE замість цього для кращої безпеки.
BladeCoder

2

Спробуйте це (Kotlin):

data class DateParcel(val date: Date?):Parcelable {
constructor(parcel: Parcel) : this(parcel.readValue(Date::class.java.classLoader) as? Date
)

override fun writeToParcel(parcel: Parcel, flags: Int) {
    parcel.writeValue(date)
}

override fun describeContents(): Int {
    return 0
}

companion object CREATOR : Parcelable.Creator<DateParcel> {
    override fun createFromParcel(parcel: Parcel): DateParcel {
        return DateParcel(parcel)
    }

    override fun newArray(size: Int): Array<DateParcel?> {
        return arrayOfNulls(size)
    }
}}

1

Dateклас реалізує Serializable...

щоб ви могли писати

parcel.writeSerializable(java.util.Date)

і ви можете читати, як

java.util.Date date = (java.util.Date)parcel.readSerializable();

1
Хоча це буде працювати, я пропоную користувачам SO взяти на себе відповідь, використовуючи longs.
Грем Сміт

0

Спробуйте це таким чином:

для запису ::

yourParse.writeSerializable(YourGivenDate)

для читання ::

Date myDate = yourParse.readSerializable();
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.