安卓传感器数据的线性化(加速度计)



我正在研究使用安卓手机中的传感器准确检测用户的脚步。我主要用加速度计传感器来检测脚的步数。我使用了一种获取加速度计数据的方法,并寻找一种去除加速度计数据中不需要的噪声的方法。我发现数据的线性化是一个好方法。但我不太清楚该怎么做。我认为这是一种中值。所以我并没有找到一种实时获取中值的方法。有人能给我一个更好的降噪方法来去除加速度计数据的噪音吗。

这是我的密码。(我使用NChart库在图表中绘制了我的加速度计数据。)

package com.android.gait;
import org.achartengine.GraphicalView;
import android.hardware.Sensor;
import android.hardware.SensorEvent;
import android.hardware.SensorEventListener;
import android.hardware.SensorListener;
import android.hardware.SensorManager;
import android.os.Bundle;
import android.app.Activity;
import android.content.Context;
import android.view.Menu;
import android.view.View;
import android.widget.LinearLayout;
import android.widget.RelativeLayout;
import android.widget.TextView;
public class MainActivity extends Activity implements SensorEventListener{
    private int count=0;
    private static GraphicalView view;
    private LineGraph line = new LineGraph();
    private static Thread thread;
    private SensorManager mSensorManager;
    private Sensor mAccelerometer;
    TextView title,tv,tv1,tv2;
    RelativeLayout layout;
    private static Point p;
static float m = 0;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
         //get the sensor service
           mSensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE);
           //get the accelerometer sensor
           mAccelerometer = mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
           //get layout
           layout = (RelativeLayout)findViewById(R.id.relative);
           LinearLayout layout = (LinearLayout) findViewById(R.id.layoutC);
           view= line.getView(this);
            layout.addView(view);
            //get textviews
           title=(TextView)findViewById(R.id.name);
           tv=(TextView)findViewById(R.id.xval);
           tv1=(TextView)findViewById(R.id.yval);
           tv2=(TextView)findViewById(R.id.zval);
           thread = new Thread(){
             int iniX=0;  
               public void run()
               {
                 while(true)
                 {
                     try {
                        Thread.sleep(1);
                    } catch (InterruptedException e) {
                        // TODO Auto-generated catch block
                        e.printStackTrace();
                    }
                    iniX=+1;
                     line.addNewPoint(iniX,m);
                     view.repaint();
                    }
                 }  

           };
           thread.start();

    }
      public final void onAccuracyChanged(Sensor sensor, int accuracy)
       {
         // Do something here if sensor accuracy changes.
       }
    @Override
     public final void onSensorChanged(SensorEvent event)
       {
        count=+1;
        // Many sensors return 3 values, one for each axis.
       float x = event.values[0];
       float y = event.values[1];
       float z = event.values[2];
       //get merged value
        m = (float) Math.sqrt(x*x+y*y+z*z);

       // p =MockData.getDataFromReceiver(count, m);

       //display values using TextView
       title.setText(R.string.app_name);
       tv.setText("X axis" +"tt"+x);
       tv1.setText("Y axis" + "tt" +y);
       tv2.setText("Z axis" +"tt" +z);
       }
    @Override
    protected void onResume()
    {
    super.onResume();
    mSensorManager.registerListener(this, mAccelerometer, SensorManager.SENSOR_DELAY_NORMAL);
    }
    @Override
    protected void onPause()
    {
    super.onPause();
    mSensorManager.unregisterListener(this);
    }
    public void LineGraphHandler(View view){

    }

}

有各种算法可以从数据中去除噪声,需要进行一些实验来找出哪种是最好的。当我最后一次不得不处理遥测数据时,我让Android将其放入CSV中,然后使用R进行分析。然而,如果你一直在使用Java,我会看看commons数学,特别是他们的卡尔曼滤波器。一个例子:

    // discrete time interval
    double dt = 0.1d;
    // position measurement noise (meter)
    double measurementNoise = 10d;
    // acceleration noise (meter/sec^2)
    double accelNoise = 0.2d;
    // A = [ 1 dt ]
    //     [ 0  1 ]
    RealMatrix A = new Array2DRowRealMatrix(new double[][] { { 1, dt }, { 0, 1 } });
    // B = [ dt^2/2 ]
    //     [ dt     ]
    RealMatrix B = new Array2DRowRealMatrix(
            new double[][] { { Math.pow(dt, 2d) / 2d }, { dt } });
    // H = [ 1 0 ]
    RealMatrix H = new Array2DRowRealMatrix(new double[][] { { 1d, 0d } });
    // x = [ 0 0 ]
    RealVector x = new ArrayRealVector(new double[] { 0, 0 });
    RealMatrix tmp = new Array2DRowRealMatrix(
            new double[][] { { Math.pow(dt, 4d) / 4d, Math.pow(dt, 3d) / 2d },
                             { Math.pow(dt, 3d) / 2d, Math.pow(dt, 2d) } });
    // Q = [ dt^4/4 dt^3/2 ]
    //     [ dt^3/2 dt^2   ]
    RealMatrix Q = tmp.scalarMultiply(Math.pow(accelNoise, 2));
    // P0 = [ 1 1 ]
    //      [ 1 1 ]
    RealMatrix P0 = new Array2DRowRealMatrix(new double[][] { { 1, 1 }, { 1, 1 } });
    // R = [ measurementNoise^2 ]
    RealMatrix R = new Array2DRowRealMatrix(
            new double[] { Math.pow(measurementNoise, 2) });
    // constant control input, increase velocity by 0.1 m/s per cycle
    RealVector u = new ArrayRealVector(new double[] { 0.1d });
    ProcessModel pm = new DefaultProcessModel(A, B, Q, x, P0);
    MeasurementModel mm = new DefaultMeasurementModel(H, R);
    KalmanFilter filter = new KalmanFilter(pm, mm);

希望这能有所帮助。如果您需要进一步的帮助,请随时留言。

最新更新