Reputation: 10233
I'm developing an Android app. I need to sort an array based off of the sorting of another. I'm sorting one (distance) based off of lowest to highest, and need for my longitude values to be sorted according to the distance. So say if distance 5 had longitude 41.2265 and distance 6 had longitude 41.2187, I would need to sort the distances from lowest to highest, {5,6}, and then sort the longitudes based off of their first pair. I have read that you could do this with a 2D array, but I would prefer not to do this. I think this also could be done with mapping, but I'm not sure how. My code is below:
Part of NearestStations.java
ArrayList<String> distancetos = new ArrayList<String>();
ArrayList<String> longitudeArray = new ArrayList<String>();
while(iterator.hasNext()){
for (int i=0; i<144;i++){
double distance = 0;
double lat_end = 0;
double lon_end = 0;
try {
lat_end = Double.parseDouble(iterator.next());
lon_end = Double.parseDouble(iterator1.next());
longitudeArray.add(Double.toString(lon_end));
Log.i("Lon_end", String.valueOf(lon_end));
} catch (NumberFormatException e) {
Log.v("Main", "Convert to Double Failed : ");
}
Location locationA = new Location("point A");
locationA.setLatitude(latitude);
locationA.setLongitude(longitude);
Location locationB = new Location("point B");
locationB.setLatitude(lat_end);
locationB.setLongitude(lon_end);
distance = locationA.distanceTo(locationB) * 0.000621371192237334;
Log.i("distancebefore", String.valueOf(distance));
String dista = Double.toString(distance);
distancetos.add(dista);
}
}
Collections.sort(distancetos);
distancea = distancetos.get(0);
distance1 = distancetos.get(1);
String Longa = longitudeArray.get(0);
String Long1 = longitudeArray.get(1);
Log.i("distanceafter", String.valueOf(distancea));
Log.i("distance1after", String.valueOf(distance1));
String[] Stations = getResources().getStringArray(R.array.Stations);
String[] Longitude = getResources().getStringArray(R.array.Longitude);
String[] Latitude = getResources().getStringArray(R.array.Latitude);
Map<String, String> myMap = new HashMap<String, String>();{
for (int i = 0; i <144; i++) {
myMap.put(Latitude[i], Stations[i]);
}
}
Map<String, String> myMap1 = new HashMap<String, String>();{
for (int h = 0; h <144; h++) {
myMap1.put(Longitude[h], Stations[h]);
}
}
String value = myMap1.get(Longa);
}
}
Thank you for your help.
Upvotes: 0
Views: 863
Reputation: 1554
I believe this is what you're looking for.
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import java.util.ListIterator;
public class GenericCachedSorter {
public static void main(String[] args) {
List<Double> distances = new ArrayList<>(Arrays.asList(1d, 2d, 3d));
sort(distances, new ToComparable<Double, Double>() {
@Override
public Double toComparable(Double distance) {
// return the longitude associated with this distance
return getLongitude(distance);
}
});
for (Double distance : distances)
System.out.println(distances);
}
public interface ToComparable<T, C extends Comparable<? super C>> {
C toComparable(T t);
}
public static <T, C extends Comparable<? super C>> void sort(List<T> list, ToComparable<T, C> function) {
class Pair implements Comparable<Pair> {
final T original;
final C comparable;
Pair(T original, C comparable) {
this.original = original;
this.comparable = comparable;
}
@Override
public int compareTo(Pair other) {
return
comparable == null && other.comparable == null ? 0 :
comparable == null ? -1 :
other.comparable == null ? 1 :
comparable.compareTo(other.comparable);
}
}
List<Pair> pairs = new ArrayList<>(list.size());
for (T original : list)
pairs.add(new Pair(original, function.toComparable(original)));
Collections.sort(pairs);
ListIterator<T> iter = list.listIterator();
for (Pair pair : pairs) {
iter.next();
iter.set(pair.original);
}
}
}
Upvotes: 2
Reputation: 4069
How about making a class for them?
public class Coord{
private int id;
private double lat;
private double long;
public double getDistanceFrom(Coord coord);
}
That should help you because it decouples locations from administrative tasks - if you were writing C your approach would be a good one. But you're writing Java.
Moreover: The for
loop will silently fail because you deplete the iterator
without checking for a hasNext()
. That's only done at the outer loop. So
int i=0;
while(iterator.hasNext() && iterator1.hasNext()){ //also check iterator1
if(i>=144) break; //that's what your for loop essentially did
double distance = 0;
double lat_end = 0;
double lon_end = 0;
try {
lat_end = Double.parseDouble(iterator.next());
lon_end = Double.parseDouble(iterator1.next());
CoordArray.add(new Coord(lat_end, lat_long));
Log.i("Lon_end", String.valueOf(lon_end));
} catch (NumberFormatException e) { ... }
//more stuff here
i++;
}/*while loop*/
Upvotes: 1