Answers:
如果您只是传递对象,那么Parcelable就是为此而设计的。与使用Java的本机序列化相比,它需要付出更多的努力,但是它的速度更快(我的意思是,WAY更快)。
在文档中,有关如何实现的一个简单示例是:
// simple class that just has one member property as an example
public class MyParcelable implements Parcelable {
private int mData;
/* everything below here is for implementing Parcelable */
// 99.9% of the time you can just ignore this
@Override
public int describeContents() {
return 0;
}
// write your object's data to the passed-in Parcel
@Override
public void writeToParcel(Parcel out, int flags) {
out.writeInt(mData);
}
// this is used to regenerate your object. All Parcelables must have a CREATOR that implements these two methods
public static final Parcelable.Creator<MyParcelable> CREATOR = new Parcelable.Creator<MyParcelable>() {
public MyParcelable createFromParcel(Parcel in) {
return new MyParcelable(in);
}
public MyParcelable[] newArray(int size) {
return new MyParcelable[size];
}
};
// example constructor that takes a Parcel and gives you an object populated with it's values
private MyParcelable(Parcel in) {
mData = in.readInt();
}
}
请注意,如果要从给定的宗地中检索多个字段,则必须按照将其放入的相同顺序(即,采用FIFO方法)进行操作。
一旦实现Parcelable
了对象,就可以通过putExtra()将它们放到Intent中:
Intent i = new Intent();
i.putExtra("name_of_extra", myParcelableObject);
然后,您可以使用getParcelableExtra()将它们拉出:
Intent i = getIntent();
MyParcelable myParcelableObject = (MyParcelable) i.getParcelableExtra("name_of_extra");
如果您的对象类实现了Parcelable和Serializable,则请确保将其强制转换为以下之一:
i.putExtra("parcelable_extra", (Parcelable) myParcelableObject);
i.putExtra("serializable_extra", (Serializable) myParcelableObject);
您需要将您的对象序列化为某种字符串表示形式。一种可能的字符串表示形式是JSON,如果您问我,最简单的在android中从JSON序列化序列的方法之一是通过Google GSON。
在这种情况下,您只需将字符串返回值从中(new Gson()).toJson(myObject);
取出并检索字符串值,fromJson
然后将其用于将其转换回您的对象。
但是,如果您的对象不是很复杂,则可能不值得这样做,您可以考虑传递该对象的单独值。
String s = (new Gson().toJson(client));
,然后Cli client = new Gson().fromJson(s, Cli.class);
您可以通过意图发送可序列化的对象
// send where details is object
ClassName details = new ClassName();
Intent i = new Intent(context, EditActivity.class);
i.putExtra("Editing", details);
startActivity(i);
//receive
ClassName model = (ClassName) getIntent().getSerializableExtra("Editing");
And
Class ClassName implements Serializable {
}
Serializable
但不Parcelable
,这是很少值得冒这个险,使之Parcelable
。
对于您知道将在应用程序内传递数据的情况,请使用“全局变量”(例如静态类)
这是Dianne Hackborn(hackbod-Google Android软件工程师)在此问题上必须说的:
对于您知道活动在同一流程中运行的情况,您可以只通过全局变量共享数据。例如,您可能有一个全局
HashMap<String, WeakReference<MyInterpreterState>>
变量,当您创建一个新的MyInterpreterState时,会为其命名一个唯一的名称,并将其放入哈希映射中。要将状态发送到另一个活动,只需将唯一名称放入哈希图中,当第二个活动启动时,它可以使用接收到的名称从哈希图中检索MyInterpreterState。
您的课程应实现Serializable或Parcelable。
public class MY_CLASS implements Serializable
完成后,您可以在putExtra上发送对象
intent.putExtra("KEY", MY_CLASS_instance);
startActivity(intent);
要获得额外费用,您只需要做
Intent intent = getIntent();
MY_CLASS class = (MY_CLASS) intent.getExtras().getSerializable("KEY");
如果您的班级实施了Parcelable使用
MY_CLASS class = (MY_CLASS) intent.getExtras().getParcelable("KEY");
希望对您有所帮助:D
Serializable
的错误。该类可以实现Parcelable
例如。
快速需求的简短答案
1.将您的类实现为可序列化。
如果您有任何内部类,也不要忘记将它们实现为Serializable!
public class SportsData implements Serializable
public class Sport implements Serializable
List<Sport> clickedObj;
2.将您的对象放入Intent
Intent intent = new Intent(SportsAct.this, SportSubAct.class);
intent.putExtra("sport", clickedObj);
startActivity(intent);
3.并在另一个活动类中接收您的对象
Intent intent = getIntent();
Sport cust = (Sport) intent.getSerializableExtra("sport");
在您的课程中实现可序列化
public class Place implements Serializable{
private int id;
private String name;
public void setId(int id) {
this.id = id;
}
public int getId() {
return id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
然后,您可以按意图传递此对象
Intent intent = new Intent(this, SecondAct.class);
intent.putExtra("PLACE", Place);
startActivity(intent);
在第二个活动中,您可以获得这样的数据
Place place= (Place) getIntent().getSerializableExtra("PLACE");
但是,当数据变大时,此方法将很慢。
您可以通过几种方法访问其他类或Activity中的变量或对象。
A.数据库
B.共享首选项。
C.对象序列化。
D.可以保存公共数据的类可以命名为Common Utilities,它取决于您。
E.通过意图和可打包接口传递数据。
这取决于您的项目需求。
A. 数据库
SQLite是一个嵌入到Android中的开源数据库。SQLite支持标准的关系数据库功能,例如SQL语法,事务和准备好的语句。
教程-http: //www.vogella.com/articles/AndroidSQLite/article.html
B. 共享首选项
假设您要存储用户名。因此,现在将有两件事:关键用户名,值值。
如何储存
// Create object of SharedPreferences.
SharedPreferences sharedPref = PreferenceManager.getDefaultSharedPreferences(this);
//now get Editor
SharedPreferences.Editor editor = sharedPref.edit();
//put your value
editor.putString("userName", "stackoverlow");
//commits your edits
editor.commit();
使用putString(),putBoolean(),putInt(),putFloat(),putLong()可以保存所需的dtatype。
如何取得
SharedPreferences sharedPref = PreferenceManager.getDefaultSharedPreferences(this);
String userName = sharedPref.getString("userName", "Not Available");
http://developer.android.com/reference/android/content/SharedPreferences.html
C. 对象序列化
如果我们要保存对象状态以通过网络发送它,或者也可以将其用于您的目的,则使用对象序列化。
使用Java Bean并将其存储在他的字段之一中,并为此使用getter和setter
JavaBean是具有属性的Java类。将属性视为私有实例变量。由于它们是私有的,因此可以从类外部访问它们的唯一方法是通过类中的方法。更改属性值的方法称为setter方法,而检索属性值的方法称为getter方法。
public class VariableStorage implements Serializable {
private String inString ;
public String getInString() {
return inString;
}
public void setInString(String inString) {
this.inString = inString;
}
}
使用以下命令在您的邮件方法中设置变量
VariableStorage variableStorage = new VariableStorage();
variableStorage.setInString(inString);
然后使用对象Serialzation序列化此对象,并在其他类中反序列化此对象。
在序列化中,对象可以表示为字节序列,其中包括对象的数据以及有关对象的类型和对象中存储的数据类型的信息。
将序列化的对象写入文件后,可以从文件中读取并反序列化它,即表示对象及其数据的类型信息和字节可用于在内存中重新创建对象。
如果您想要此教程,请参考此链接
http://javawithswaranga.blogspot.in/2011/08/serialization-in-java.html
D. 公用事业
您可以自己创建一个类,其中可以包含项目中经常需要的通用数据。
样品
public class CommonUtilities {
public static String className = "CommonUtilities";
}
E. 通过意图传递数据
请参阅本教程以了解此传递数据的选项。
您可以使用android BUNDLE来做到这一点。
从您的班级创建一个捆绑包,例如:
public Bundle toBundle() {
Bundle b = new Bundle();
b.putString("SomeKey", "SomeValue");
return b;
}
然后将这个捆绑包与INTENT一起传递。现在,您可以通过传递如下捆绑包来重新创建类对象
public CustomClass(Context _context, Bundle b) {
context = _context;
classMember = b.getString("SomeKey");
}
在您的Custom类中声明并使用。
感谢您的包裹帮助,但我发现了另一种可选解决方案
public class getsetclass implements Serializable {
private int dt = 10;
//pass any object, drwabale
public int getDt() {
return dt;
}
public void setDt(int dt) {
this.dt = dt;
}
}
活动一
getsetclass d = new getsetclass ();
d.setDt(50);
LinkedHashMap<String, Object> obj = new LinkedHashMap<String, Object>();
obj.put("hashmapkey", d);
Intent inew = new Intent(SgParceLableSampelActivity.this,
ActivityNext.class);
Bundle b = new Bundle();
b.putSerializable("bundleobj", obj);
inew.putExtras(b);
startActivity(inew);
在活动2中获取数据
try { setContentView(R.layout.main);
Bundle bn = new Bundle();
bn = getIntent().getExtras();
HashMap<String, Object> getobj = new HashMap<String, Object>();
getobj = (HashMap<String, Object>) bn.getSerializable("bundleobj");
getsetclass d = (getsetclass) getobj.get("hashmapkey");
} catch (Exception e) {
Log.e("Err", e.getMessage());
}
我使用Gson及其强大而简单的API在活动之间发送对象,
例
// This is the object to be sent, can be any object
public class AndroidPacket {
public String CustomerName;
//constructor
public AndroidPacket(String cName){
CustomerName = cName;
}
// other fields ....
// You can add those functions as LiveTemplate !
public String toJson() {
Gson gson = new Gson();
return gson.toJson(this);
}
public static AndroidPacket fromJson(String json) {
Gson gson = new Gson();
return gson.fromJson(json, AndroidPacket.class);
}
}
将它们添加到要发送的对象中的2个功能
用法
将对象从A发送到B
// Convert the object to string using Gson
AndroidPacket androidPacket = new AndroidPacket("Ahmad");
String objAsJson = androidPacket.toJson();
Intent intent = new Intent(A.this, B.class);
intent.putExtra("my_obj", objAsJson);
startActivity(intent);
在B接收
@Override
protected void onCreate(Bundle savedInstanceState) {
Bundle bundle = getIntent().getExtras();
String objAsJson = bundle.getString("my_obj");
AndroidPacket androidPacket = AndroidPacket.fromJson(objAsJson);
// Here you can use your Object
Log.d("Gson", androidPacket.CustomerName);
}
我几乎在每个项目中都使用它,并且没有性能问题。
在您的第一个活动中:
intent.putExtra("myTag", yourObject);
在第二个中:
myCustomObject myObject = (myCustomObject) getIntent().getSerializableExtra("myTag");
不要忘记使您的自定义对象可序列化:
public class myCustomObject implements Serializable {
...
}
另一种方法是使用Application
对象(android.app.Application)。您在AndroidManifest.xml
文件中将其定义为:
<application
android:name=".MyApplication"
...
然后,您可以从任何活动中调用此方法并将对象保存到 Application
类中。
在FirstActivity中:
MyObject myObject = new MyObject();
MyApplication app = (MyApplication) getApplication();
app.setMyObject(myObject);
在SecondActivity中,执行以下操作:
MyApplication app = (MyApplication) getApplication();
MyObject retrievedObject = app.getMyObject(myObject);
如果您的对象具有应用程序级别范围,即必须在整个应用程序中使用它们,这将很方便。Parcelable
如果要显式控制对象范围或范围受到限制,则该方法仍然更好。
但是,这Intents
完全避免了使用。我不知道他们是否适合您。我使用此方法的另一种方法是让int
对象的标识符通过意图发送并检索对象在Maps中具有的Application
对象。
Map
通过将标识符用于存储和检索对象的应用程序范围,我已经成功地将其用于从Web服务生成的对象。这种方法的唯一真正的问题是,Android会在一段时间后清除内存,因此您必须检查onResume上的空值(我认为在意图中传递的对象是持久性的,但不确定)。除此之外,我认为这并不逊色。
在您的类模型(对象)中实现Serializable,例如:
public class MensajesProveedor implements Serializable {
private int idProveedor;
public MensajesProveedor() {
}
public int getIdProveedor() {
return idProveedor;
}
public void setIdProveedor(int idProveedor) {
this.idProveedor = idProveedor;
}
}
和你的第一个活动
MensajeProveedor mp = new MensajeProveedor();
Intent i = new Intent(getApplicationContext(), NewActivity.class);
i.putExtra("mensajes",mp);
startActivity(i);
还有第二个活动(NewActivity)
MensajesProveedor mensajes = (MensajesProveedor)getIntent().getExtras().getSerializable("mensajes");
祝好运!!
public class SharedBooking implements Parcelable{
public int account_id;
public Double betrag;
public Double betrag_effected;
public int taxType;
public int tax;
public String postingText;
public SharedBooking() {
account_id = 0;
betrag = 0.0;
betrag_effected = 0.0;
taxType = 0;
tax = 0;
postingText = "";
}
public SharedBooking(Parcel in) {
account_id = in.readInt();
betrag = in.readDouble();
betrag_effected = in.readDouble();
taxType = in.readInt();
tax = in.readInt();
postingText = in.readString();
}
public int getAccount_id() {
return account_id;
}
public void setAccount_id(int account_id) {
this.account_id = account_id;
}
public Double getBetrag() {
return betrag;
}
public void setBetrag(Double betrag) {
this.betrag = betrag;
}
public Double getBetrag_effected() {
return betrag_effected;
}
public void setBetrag_effected(Double betrag_effected) {
this.betrag_effected = betrag_effected;
}
public int getTaxType() {
return taxType;
}
public void setTaxType(int taxType) {
this.taxType = taxType;
}
public int getTax() {
return tax;
}
public void setTax(int tax) {
this.tax = tax;
}
public String getPostingText() {
return postingText;
}
public void setPostingText(String postingText) {
this.postingText = postingText;
}
public int describeContents() {
// TODO Auto-generated method stub
return 0;
}
public void writeToParcel(Parcel dest, int flags) {
dest.writeInt(account_id);
dest.writeDouble(betrag);
dest.writeDouble(betrag_effected);
dest.writeInt(taxType);
dest.writeInt(tax);
dest.writeString(postingText);
}
public static final Parcelable.Creator<SharedBooking> CREATOR = new Parcelable.Creator<SharedBooking>()
{
public SharedBooking createFromParcel(Parcel in)
{
return new SharedBooking(in);
}
public SharedBooking[] newArray(int size)
{
return new SharedBooking[size];
}
};
}
传递数据:
Intent intent = new Intent(getApplicationContext(),YourActivity.class);
Bundle bundle = new Bundle();
i.putParcelableArrayListExtra("data", (ArrayList<? extends Parcelable>) dataList);
intent.putExtras(bundle);
startActivity(intent);
检索数据:
Bundle bundle = getIntent().getExtras();
dataList2 = getIntent().getExtras().getParcelableArrayList("data");
我找到的最简单的解决方案是..创建一个带有带有getters setter的静态数据成员的类。
从一个活动中设置并从另一个活动中获取该对象。
活动A
mytestclass.staticfunctionSet("","",""..etc.);
活动b
mytestclass obj= mytestclass.staticfunctionGet();
创建Android应用程序
文件>>新建>> Android应用程序
输入项目名称:android-pass-object-to-activity
包:com.hmkcode.android
保留其他默认设置,转到下一步,直到完成
在开始创建App之前,我们需要创建POJO类“ Person”,我们将使用该类将对象从一个活动发送到另一个活动。注意,该类正在实现Serializable接口。
人.java
package com.hmkcode.android;
import java.io.Serializable;
public class Person implements Serializable{
private static final long serialVersionUID = 1L;
private String name;
private int age;
// getters & setters....
@Override
public String toString() {
return "Person [name=" + name + ", age=" + age + "]";
}
}
两种活动的两种布局
activity_main.xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context=".MainActivity" >
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:orientation="horizontal">
<TextView
android:id="@+id/tvName"
android:layout_width="100dp"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:gravity="center_horizontal"
android:text="Name" />
<EditText
android:id="@+id/etName"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:ems="10" >
<requestFocus />
</EditText>
</LinearLayout>
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:orientation="horizontal">
<TextView
android:id="@+id/tvAge"
android:layout_width="100dp"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:gravity="center_horizontal"
android:text="Age" />
<EditText
android:id="@+id/etAge"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:ems="10" />
</LinearLayout>
<Button
android:id="@+id/btnPassObject"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:text="Pass Object to Another Activity" />
</LinearLayout>
activity_another.xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
>
<TextView
android:id="@+id/tvPerson"
android:layout_height="wrap_content"
android:layout_width="fill_parent"
android:layout_gravity="center"
android:gravity="center_horizontal"
/>
</LinearLayout>
两种活动课程
1)ActivityMain.java
package com.hmkcode.android;
import android.os.Bundle;
import android.app.Activity;
import android.content.Intent;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
public class MainActivity extends Activity implements OnClickListener {
Button btnPassObject;
EditText etName, etAge;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
btnPassObject = (Button) findViewById(R.id.btnPassObject);
etName = (EditText) findViewById(R.id.etName);
etAge = (EditText) findViewById(R.id.etAge);
btnPassObject.setOnClickListener(this);
}
@Override
public void onClick(View view) {
// 1. create an intent pass class name or intnet action name
Intent intent = new Intent("com.hmkcode.android.ANOTHER_ACTIVITY");
// 2. create person object
Person person = new Person();
person.setName(etName.getText().toString());
person.setAge(Integer.parseInt(etAge.getText().toString()));
// 3. put person in intent data
intent.putExtra("person", person);
// 4. start the activity
startActivity(intent);
}
}
2)AnotherActivity.java
package com.hmkcode.android;
import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.widget.TextView;
public class AnotherActivity extends Activity {
TextView tvPerson;
@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_another);
// 1. get passed intent
Intent intent = getIntent();
// 2. get person object from intent
Person person = (Person) intent.getSerializableExtra("person");
// 3. get reference to person textView
tvPerson = (TextView) findViewById(R.id.tvPerson);
// 4. display name & age on textView
tvPerson.setText(person.toString());
}
}
使用谷歌的Gson库,您可以将对象传递给另一个活动。实际上,我们将以json字符串的形式转换对象,并在传递给其他活动后再次将其转换为这样的对象
考虑这样的bean类
public class Example {
private int id;
private String name;
public Example(int id, String name) {
this.id = id;
this.name = name;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
我们需要传递Example类的对象
Example exampleObject=new Example(1,"hello");
String jsonString = new Gson().toJson(exampleObject);
Intent nextIntent=new Intent(this,NextActivity.class);
nextIntent.putExtra("example",jsonString );
startActivity(nextIntent);
为了阅读,我们需要在NextActivity中执行相反的操作
Example defObject=new Example(-1,null);
//default value to return when example is not available
String defValue= new Gson().toJson(defObject);
String jsonString=getIntent().getExtras().getString("example",defValue);
//passed example object
Example exampleObject=new Gson().fromJson(jsonString,Example .class);
在gradle中添加此依赖项
compile 'com.google.code.gson:gson:2.6.2'
Intent i = new Intent();
i.putExtra("name_of_extra", myParcelableObject);
startACtivity(i);
如果您仍然有一个单例类(fx服务)充当模型层的网关,则可以通过在该类中具有一个带有getter和setter的变量来解决。
在活动1中:
Intent intent = new Intent(getApplicationContext(), Activity2.class);
service.setSavedOrder(order);
startActivity(intent);
在活动2中:
private Service service;
private Order order;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_quality);
service = Service.getInstance();
order = service.getSavedOrder();
service.setSavedOrder(null) //If you don't want to save it for the entire session of the app.
}
服务中:
private static Service instance;
private Service()
{
//Constructor content
}
public static Service getInstance()
{
if(instance == null)
{
instance = new Service();
}
return instance;
}
private Order savedOrder;
public Order getSavedOrder()
{
return savedOrder;
}
public void setSavedOrder(Order order)
{
this.savedOrder = order;
}
该解决方案不需要对所讨论对象进行任何序列化或其他“打包”操作。但这只会在您无论如何都使用这种架构的情况下才是有益的。
到目前为止,恕我直言,最简单的方式来打包对象。您只需在要使其可拆分的对象上方添加注释标签。
库中的一个示例位于https://github.com/johncarl81/parceler
@Parcel
public class Example {
String name;
int age;
public Example(){ /*Required empty bean constructor*/ }
public Example(int age, String name) {
this.age = age;
this.name = name;
}
public String getName() { return name; }
public int getAge() { return age; }
}
首先在您的课程中实现 Parcelable。然后像这样传递对象。
SendActivity.java
ObjectA obj = new ObjectA();
// Set values etc.
Intent i = new Intent(this, MyActivity.class);
i.putExtra("com.package.ObjectA", obj);
startActivity(i);
ReceiveActivity.java
Bundle b = getIntent().getExtras();
ObjectA obj = b.getParcelable("com.package.ObjectA");
包字符串不是必需的,只是两个活动中的字符串都必须相同
通过Bundle Object从此活动传递参数开始另一个活动
Intent intent = new Intent(getBaseContext(), YourActivity.class);
intent.putExtra("USER_NAME", "xyz@gmail.com");
startActivity(intent);
检索另一个活动(YourActivity)
String s = getIntent().getStringExtra("USER_NAME");
对于简单种类的数据类型来说可以。但是,如果您想在两次活动之间传递复杂的数据,则需要先对其进行序列化。
这里有员工模型
class Employee{
private String empId;
private int age;
print Double salary;
getters...
setters...
}
您可以使用Google提供的Gson lib来序列化复杂数据,如下所示
String strEmp = new Gson().toJson(emp);
Intent intent = new Intent(getBaseContext(), YourActivity.class);
intent.putExtra("EMP", strEmp);
startActivity(intent);
Bundle bundle = getIntent().getExtras();
String empStr = bundle.getString("EMP");
Gson gson = new Gson();
Type type = new TypeToken<Employee>() {
}.getType();
Employee selectedEmp = gson.fromJson(empStr, type);
在科特丁
在您的build.gradle中添加kotlin扩展名。
apply plugin: 'kotlin-android-extensions'
android {
androidExtensions {
experimental = true
}
}
然后像这样创建您的数据类。
@Parcelize
data class Sample(val id: Int, val name: String) : Parcelable
意图传递对象
val sample = Sample(1,"naveen")
val intent = Intent(context, YourActivity::class.java)
intent.putExtra("id", sample)
startActivity(intent)
意图获取对象
val sample = intent.getParcelableExtra("id")
最简单的Java方法是:在pojo / model类中实现可序列化
推荐用于Android以获得性能视图:使模型可分解
最简单的方法是在项目为字符串的情况下使用以下代码:
intent.putextra("selected_item",item)
接收:
String name = data.getStringExtra("selected_item");