Android - 保存自定义对象 - 共享首选项或数据库?

Posted

技术标签:

【中文标题】Android - 保存自定义对象 - 共享首选项或数据库?【英文标题】:Android - Saving custom object - Shared Preferences or Database? 【发布时间】:2014-03-12 19:09:55 【问题描述】:

我正在创建一个基于位置的提醒应用程序。

我有一个名为 Reminder 的自定义对象,它存储纬度、经度、位置名称和提醒的主题 - 以及它所属的个人资料。

然后我将位置名称和主题输入到 ListView(这里也使用 cardlibs)。

但是现在我需要在关闭应用程序时保存数据,并且想知道解决此问题的最佳方法 - 我是存储整个“提醒”对象还是仅在共享首选项中存储多条数据/ 一个数据库。

这是我的代码 - 它非常低效/丑陋:

提醒:

public class Reminder implements Parcelable 

public double latitude;
public double longitude;
public String subject;
public String locationName;

public String profile;

public Reminder() 



public Reminder(Parcel in) 
    String[] data = new String[5];

    in.readStringArray(data);
    this.subject = data[0];
    this.locationName = data[1];
    this.latitude = Double.parseDouble(data[2]);
    this.longitude = Double.parseDouble(data[3]);
    this.profile = data[4];



public String getProfile() 
    return profile;


public double getLatitude() 
    return latitude;


public String getLocationName() 
    return locationName;


public double getLongitude() 
    return longitude;


public String getSubject() 
    return subject;


public void setProfile(String profile) 
    this.profile = profile;


public void setLatitude(double latitude) 
    this.latitude = latitude;


public void setLocationName(String locationName) 
    this.locationName = locationName;


public void setLongitude(double longitude) 
    this.longitude = longitude;


public void setSubject(String subject) 
    this.subject = subject;


@Override
public int describeContents() 
    return 0;


@Override
public void writeToParcel(Parcel dest, int flags) 

    dest.writeStringArray(new String[]  this.subject, this.locationName,
            String.valueOf(this.latitude), String.valueOf(this.longitude), this.profile );


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

    public Reminder createFromParcel(Parcel source) 
        // TODO Auto-generated method stub
        return new Reminder(source); // using parcelable constructor
    

    public Reminder[] newArray(int size) 
        // TODO Auto-generated method stub
        return new Reminder[size];
    

;

使用片段列出:

public class HomeFragment extends Fragment 

public static ArrayList<Card> cards = new ArrayList<Card>();

Reminder reminder;

public HomeFragment() 


@Override
public void onActivityCreated(Bundle savedInstanceState) 
    // TODO Auto-generated method stub
    super.onActivityCreated(savedInstanceState);

    reminder = getActivity().getIntent().getParcelableExtra("reminder");

    Card card = new Card(getActivity());

    CardHeader cardHeader = new CardHeader(getActivity());

    if (reminder != null) 
        cardHeader.setTitle(reminder.getSubject());
        card.addCardHeader(cardHeader);
        card.setTitle(reminder.getLocationName());
        cards.add(card);
    

    CardArrayAdapter mCardArrayAdapter = new CardArrayAdapter(
            getActivity(), cards);

    CardListView listView = (CardListView) getActivity().findViewById(
            R.id.card_list);
    mCardArrayAdapter.notifyDataSetChanged();
    if (listView != null)
        listView.setAdapter(mCardArrayAdapter);





任何关于如何更好地编写我的代码的批评也将非常有益,因为我觉得我是一个巨大的菜鸟,并且错过了一些明显可以提高效率的东西。

谢谢!

【问题讨论】:

这个属于codereview.stackexchange.com 对不起,直到现在才听说过。谢谢! 【参考方案1】:

基本上,选择使用共享偏好还是使用数据库取决于许多因素:

1) 我们在谈论多少个对象?它们有多复杂?

2) 您打算搜索/操作这些对象还是只是保存/加载它们。

3) 您是否打算导出/移动/发送对象?

4) 您是否希望对象可以跨应用程序上下文进行恢复 - 这不仅仅是有问题的单个应用程序。

在您的具体情况下,我会使用数据库。

http://developer.android.com/guide/topics/data/data-storage.html#pref

正如您在此处的文档中看到的,prefs 并不是真正用于对象存储 - 它是用于键值对。虽然您可以将一个对象作为多个键值对存储在共享首选项中并从那里进行重构,但您必须通过一些奇怪的模型转换来为多个对象执行此操作。简而言之,它没有任何意义。

【讨论】:

如果我要使用数据库,创建自定义对象“提醒”会有多大用处?而是在创建“提醒”对象时,将其与相应数据一起输入到数据库中。每次使用数据库中的数据创建片段时,都会重新填充 ListView。 这取决于几件事 - 主要是您打算如何处理提醒。查看:developer.android.com/reference/android/widget/… 了解直接从数据库转换为列表视图的好方法 提醒只是作为接近警报。提醒将只是在具有编辑或删除功能的列表中。至于为什么元数据必须包含在 ListView 中,以便用户可以查看和编辑它。感谢您提供这些链接,我会仔细查看。

以上是关于Android - 保存自定义对象 - 共享首选项或数据库?的主要内容,如果未能解决你的问题,请参考以下文章

Flutter 存储共享首选项中的自定义类列表

如何将 HashMap 保存到共享首选项?

将自定义可序列化对象绑定到控件,以便用户和加载/保存首选项

如何以共享首选项保存图像?

在共享首选项中保存按钮的颜色(kotlin)

在 Xamarin.Android 中将 Json 对象项中的错误值保存和检索到 IShared 首选项(始终返回注销值)