JSON对象在数组中意外重复

时间:2019-05-16 19:41:49

标签: java android json

我正在编写一个记录传感器数据的android应用程序。 试图将这些数据保存到json文件中,但是json数组原来是用最近的测量值重复该数组的项。

(?<= )

当前状态'mSensorState'的数据作为json对象正确移位。按预期更新

private JSONObject mSensorState = new JSONObject();
private JSONArray mSensorBuffArray = new JSONArray();

@Override
public void onSensorChanged(SensorEvent sensorEvent) {
  ...
  mSensorState.put("HR",HR_data);
  mSensorState.put("Step",Step_Data);
  mSensorBuffArray.put(mSensorState);
  Log.d(TAG,"JSON "+ mSensorState.toString());
  Log.d(TAG,"JSON "+ mSensorBuffArray.toString());
}

但是数组没有。它显示为一系列最新测量值。

JSON {"HR":"95","Step":"10328"}
JSON {"HR":"96","Step":"10328"}
JSON {"HR":"98","Step":"10328"}

1 个答案:

答案 0 :(得分:1)

mSensorState的无效是有缺陷的。

我猜在...省略的某个地方,有一个

mSensorState.clear();

但实际上应该是

mSensorState = new JSONObject();

这可以归结为Java内存模型,对此进行了here on Stackoverflow的全面解释。那里的评论之一构成了一个不错的类比:

mSensorState视为气球。但是,在Java中,您实际上从未持有过气球,而是始终持有一个字符串。考虑到这一点,让我们看一下通话

mSensorBuffArray.put(mSensorState);

首先,将第二个字符串附加到balloon,并传递给方法调用。在该方法期间,mSensorBuffArray将保留其最新索引中传递的字符串。

一旦使用相同的对象引用再次调用此方法,将再次发生相同的事情,并且mSensorBuffArray将在两个不同的索引处将两个字符串保存在相同气球中。因此,通过两个索引都可以看到对该气球所做的更改。

现在,返回

mSensorState = new JSONObject();

这种方式会剪切您当前持有的字符串,并将其附加到新的气球上。旧气球没有消失,因为它可能已连接了其他绳子。如果没有留下任何字符串,java最终将在将来的某个时候破坏气球。


如果适用,也可以通过将JSONObject转换为局部变量来将其绑定到方法的范围:

public void onSensorChanged(SensorEvent sensorEvent) {
    ...
    JSONObject sensorState = new JSONObject();
    sensorState.put("HR",HR_data);
    sensorState.put("Step",Step_Data);
    mSensorBuffArray.put(sensorState);

如果在其他方法中需要,则仍可以从JSONArray获取最新值:(假设它实现了List

private void internalStuff(/*whatever you need*/) {
    JSONObject sensorState = mSensorBuffArray.get(mSensorBuffArray.size() - 1);