问题描述
我有一个数组列表,ArrayList(),用于保存 lat 和 lng.然后当有新点时会画一条线.我想获取此数组中的元素,以计算总距离.但是不知何故我使用calculateDistance方法来计算总距离,结果不正确.所以我想知道我是否做错了什么.
I have an array list, ArrayList(), which is used to save lat and lng. And then a line will be drawn when there is a new point. I want to get the element inside this array, in order to calculate the total distance. But somehow i use the calculateDistance Method to calculate the total distance, the result is not correct. So i want to know if i had do something wrong.
private void whereAmI(){
Location location = manager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
updateWithNewLocation(location);
//GPS Listener
manager.addGpsStatusListener(gpsListener);
//Location Listener
int minTime = 0;//ms
int minDist = 0;//meter
manager.requestLocationUpdates(LocationManager.GPS_PROVIDER, minTime, minDist, locationListener);
}
GpsStatus.Listener gpsListener = new GpsStatus.Listener() {
@Override
public void onGpsStatusChanged(int event) {
switch (event) {
case GpsStatus.GPS_EVENT_STARTED:
Log.d("x=", "GPS_EVENT_STARTED");
Toast.makeText(MapsActivity.this, "GPS_EVENT_STARTED", Toast.LENGTH_SHORT).show();
break;
case GpsStatus.GPS_EVENT_STOPPED:
Log.d("x=", "GPS_EVENT_STOPPED");
Toast.makeText(MapsActivity.this, "GPS_EVENT_STOPPED", Toast.LENGTH_SHORT).show();
break;
case GpsStatus.GPS_EVENT_FIRST_FIX:
Log.d("x=", "GPS_EVENT_FIRST_FIX");
Toast.makeText(MapsActivity.this, "GPS_EVENT_FIRST_FIX", Toast.LENGTH_SHORT).show();
break;
case GpsStatus.GPS_EVENT_SATELLITE_STATUS:
Log.d("x=", "GPS_EVENT_SATELLITE_STATUS");
break;
}
}
};
LocationListener locationListener = new LocationListener(){
@Override
public void onLocationChanged(Location location) {
updateWithNewLocation(location);
}
@Override
public void onProviderDisabled(String provider) {
updateWithNewLocation(null);
}
@Override
public void onProviderEnabled(String provider) {
}
@Override
public void onStatusChanged(String provider, int status, Bundle extras) {
switch (status) {
case LocationProvider.OUT_OF_SERVICE:
Log.v("x=", "Status Changed: Out of Service");
Toast.makeText(MapsActivity.this, "Status Changed: Out of Service", Toast.LENGTH_SHORT).show();
break;
case LocationProvider.TEMPORARILY_UNAVAILABLE:
Log.v("x=", "Status Changed: Temporarily Unavailable");
Toast.makeText(MapsActivity.this, "Status Changed: Temporarily Unavailable", Toast.LENGTH_SHORT).show();
break;
case LocationProvider.AVAILABLE:
Log.v("x=", "Status Changed: Available");
Toast.makeText(MapsActivity.this, "Status Changed: Available", Toast.LENGTH_SHORT).show();
break;
}
}
};
private void showMarkerMe(double lat, double lng){
if (markerMe != null) {
markerMe.remove();
}
MarkerOptions markerOpt = new MarkerOptions();
markerOpt.position(new LatLng(lat, lng));
markerOpt.title("I am here!");
markerMe = mMap.addMarker(markerOpt);
//Toast.makeText(this, "lat:" + lat + ",lng:" + lng, Toast.LENGTH_SHORT).show();
}
private void cameraFocusOnMe(double lat, double lng){
CameraPosition camPosition = new CameraPosition.Builder()
.target(new LatLng(lat, lng))
.zoom(16)
.build();
mMap.animateCamera(CameraUpdateFactory.newCameraPosition(camPosition));
}
private void trackToMe(double lat, double lng){
if (traceOfMe == null) {
traceOfMe = new ArrayList<LatLng>();
}
traceOfMe.add(new LatLng(lat, lng));
calculateDistance(traceOfMe);
PolylineOptions polylineOpt = new PolylineOptions();
for (LatLng latlng : traceOfMe) {
polylineOpt.add(latlng);
}
polylineOpt.color(Color.RED);
Polyline line = mMap.addPolyline(polylineOpt);
line.setWidth(10);
}
private void calculateDistance(ArrayList<LatLng> points) {
for (int i =0; i < points.size() -1; i++) {
LatLng pointA = points.get(i);
LatLng pointB = points.get(i + 1);
float[] results = new float[3];
Location.distanceBetween (pointA.latitude, pointA.longitude, pointB.latitude, pointB.longitude, results);
totalD += results[0];
}
}
private void updateWithNewLocation(Location location) {
String where = "";
if (location != null) {
double lng = location.getLongitude();
double lat = location.getLatitude();
float speed = location.getSpeed();
long time = location.getTime();
String timeString = getTimeString(time);
speedList.add(""+ speed);
where = "Lng: " + lng +
" Lat: " + lat +
" Speed: " + speed +
"\nTime: " + timeString +
" Provider: " + "gps" +
" Distance: " + totalD ;
showMarkerMe(lat, lng);
cameraFocusOnMe(lat, lng);
trackToMe(lat, lng);
}else{
where = "No location found.";
}
txt.setText(where);
}
推荐答案
我不确定 totalD
变量是在哪里声明的,但它似乎在您添加的每个点上累积值列表.假设您从 A 点步行到 B 点,距离为 10 米,因此您的初始 ArrayList 仅包含 2 个点,当您计算距离时,它被正确计算为 10 米并分配给 totalD 变量.现在你走得更远,从 B 点到 C 点,再走 5 米,你的 ArrayList 现在包含 3 个点 A、B 和 C,总距离应该是 15 米 (10 + 5).按照您编写函数的方式,您可以浏览点列表,并将其全部添加到 totalD 中,而无需重新设置它.因此,您的 totalD 已经从之前的计算中获得了 10 的值,现在通过再次遍历 ArrayList 并获得总计 15,您可以将该 15 添加到您在第一次计算中获得的前 10 中.您的 totalD 现在是 25(10 + 15,之前所有计算的结果相加),而不是简单的 15(仅最后一次计算的结果).所以在你的 calculateDistance()
方法而不是
I'm not sure where the totalD
variable is declared, but it seems like it is accumulating values with each point you add to the list. Say you walk from point A to point B with a distance of 10 meters, so your initial ArrayList contains only 2 points and when you calculate the distance it is correctly calculated as 10 meters and assigned to totalD variable. Now you walk further, from point B to point C, say another 5 meters, and your ArrayList now contains 3 points A, B, and C, with a total distance that's supposed to be 15 meters (10 + 5). The way your function was written, you go through the list of points, and add it all to totalD without ever re-setting it. So, your totalD already had a value of 10 from the previous calculation, and now by going through the ArrayList again and getting a total of 15, you add that 15 to the previous 10 that you had there from the first calculation. Your totalD is now 25 (10 + 15, the results of all previous calculations combined), instead of simply 15 (the result of only the last calculation). So in your calculateDistance()
method instead of
totalD += results[0];
你应该有一个局部变量,比如tempTotalDistance
,然后将点之间的所有距离添加到其中,然后将其最终值分配给全局totalD
.你的新 calculateDistance()
看起来像这样:
you should have a local variable, say tempTotalDistance
, and then add all distances between points into it, and then assign its final value to your global totalD
. Your new calculateDistance()
can look something like this:
private void calculateDistance(ArrayList<LatLng> points) {
float tempTotalDistance;
for (int i =0; i < points.size() -1; i++) {
LatLng pointA = points.get(i);
LatLng pointB = points.get(i + 1);
float[] results = new float[3];
Location.distanceBetween (pointA.latitude, pointA.longitude, pointB.latitude, pointB.longitude, results);
tempTotalDistance += results[0];
}
totalD = tempTotalDistance;
}
这篇关于如何计算总行驶距离?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!