1

我有一个自定义 UITableView,由带入 NSMutableDictionary 的 JSON 数据填充。然后我创建一个 mutablecopy,以便我可以将 distanceFromLocation 方法的值添加到字典中。我要做的是然后使用该新对象按最近距离对单元格进行排序。我看过其他使用 NSSortDescriptor 的例子,但那是在谈论排序数组。如何对字典中的单元格进行排序或从字典中创建一个数组以使用 NSSortDescriptor?

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath 
{

static NSString *CellIdentifier = @"dealerlistcell";

DealerListCell *cell = (DealerListCell *)[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) 
{
    cell = [[DealerListCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:CellIdentifier];
}

//gets JSON data and loads into Dictionary
NSMutableDictionary *info = [json objectAtIndex:indexPath.row];
NSMutableDictionary *infocopy = [info mutableCopy];

//pulls the current user location
CLLocation *currentlocation2 = [[CLLocation alloc] initWithLatitude:locationManager.location.coordinate.latitude longitude:locationManager.location.coordinate.longitude];

//gets the latitude and longitude from info dictionary to calculate distancefromlocation for each cell
CLLocation *locationforindex = [[CLLocation alloc] initWithLatitude:[[info objectForKey:@"dlrlat"]doubleValue] longitude:[[info objectForKey:@"dlrlong"]doubleValue]];

//calculates the distance
CLLocationDistance dist = ([locationforindex distanceFromLocation:currentlocation2]*0.0006213711922);

//format the distance to a string for the label
NSString *distancestring = [NSString stringWithFormat:@"%.1f miles",dist];

//create object with distance to add to dictionary
NSNumber *distance = [NSNumber numberWithDouble:dist];

编辑:分配到对象的距离,以便稍后在 NSSortDescriptor 中调用

//add to dictionary 
[infocopy setObject:distance forKey:@"distance"];

//create array from dictionary
NSDictionary *aDict = [NSDictionary dictionaryWithDictionary:infocopy];
NSArray *anArray = [aDict allValues];

//implemented NSSortDescriptor
NSSortDescriptor *sorter [[NSSortDescriptor alloc] initWithKey:@"distance" ascending: YES];
NSArray *sortdescriptors = [NSArray arrayWithObject:sorter];
[anArray sortedArrayUsingDescriptors:sortdescriptors];

但是,它会为键距离抛出 valueForUndefinedKey。如何在“initWithKey”中定义距离键?

4

2 回答 2

1

通过这个论坛和我朋友的一些帮助,我能够拼凑出这个解决方案。

答案是在加载表格视图之前使用 for 循环并为方法中的每个位置创建字典。然后我使用 NSSortDescriptor 进行排序,它工作得很好。

有关最终解决方案,请参见下面的代码。

-(void)getData:(NSData *) data 
{

NSError *error;

// load the jsonArray with the JSON Data
jsonArray = [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&error];


//define the unsorted dealers array
unsortedDealers = [[NSMutableArray alloc] initWithCapacity:1000];

// start at row 0
int index = 0;

// loop through each dealer and calculate distance from current location
for (NSDictionary *dealer in jsonArray) 
{
    //create dictionary from JSON Array
    infoDict = [jsonArray objectAtIndex:index];

    //get the coordidates from current location
    CLLocation *currentlocation = [[CLLocation alloc] initWithLatitude:locationManager.location.coordinate.latitude longitude:locationManager.location.coordinate.longitude];

    //get the coordinates for dealer at row
    // dlr lat and longs are switched in the database
    CLLocation *locationforindex = [[CLLocation alloc] initWithLatitude:[[infoDict objectForKey:@"dlrlong"]doubleValue] longitude:[[infoDict objectForKey:@"dlrlat"]doubleValue]];

    //calculate the distance from current location to dealer at row and format it in miles
    CLLocationDistance dist = ([locationforindex distanceFromLocation:currentlocation]*0.0006213711922);

    //define the distance for display
    NSNumber *distanceForDict = [NSNumber numberWithDouble:dist];

    //define the distance for sorting
    NSString *distanceForSort = [NSString stringWithFormat:@"%.1f",dist];

   //create a dictionary for each dealer and define the values for each key 
   NSMutableDictionary *dealerDict = [[NSMutableDictionary alloc] initWithObjectsAndKeys:[infoDict objectForKey:@"dlrname"] , @"dlrname", [infoDict objectForKey:@"dlrcity"], @"dlrcity", [infoDict objectForKey:@"dlrstate"] , @"dlrstate", [infoDict objectForKey:@"dlrzip"], @"dlrzip", [infoDict objectForKey:@"dlradd"] , @"dlradd", distanceForDict , @"dlrdistance" , distanceForSort , @"dlrsortdistance" , [infoDict objectForKey:@"dlremail"] , @"dlremail" , [infoDict objectForKey:@"dlrfax"] , @"dlrfax" , [infoDict objectForKey:@"dlrhours"] , @"dlrhours" , [infoDict objectForKey:@"dlrlat"], @"dlrlat",[infoDict objectForKey:@"dlrlong"] , @"dlrlong" , [infoDict objectForKey:@"dlrnum"], @"dlrnum",[infoDict objectForKey:@"dlrphone"] , @"dlrphone" , [infoDict objectForKey:@"dlrwebsite"], @"dlrwebsite", nil];

    //add dictionary to the unsorted array
    [unsortedDealers addObject:dealerDict];

    // iterate through the list of dealers
    ++index;

}

// creates the sorting element
NSSortDescriptor *sortDescriptor;

//define what you want to sort by
sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"dlrdistance" ascending:YES];

// build new array with thosed elements to be sorted
NSArray *sortDescriptors = [NSArray arrayWithObject:sortDescriptor];

// create new array based on the sorted value
sortedDealers = [unsortedDealers sortedArrayUsingDescriptors:sortDescriptors];  

[self.tableView reloadData];

//error message if there is no data found. Usually this is an error with the connection, 
//it should never return empty
if (jsonArray ==  nil) 
{
    NSLog(@"No Data Loaded. Please check your internet connection");
}

}

于 2012-05-07T22:19:35.943 回答
0

如果你这样做:

NSDictionary *aDict = [NSDictionary dictionaryWithDictionary:info];
NSArray *anArray = [aDict allValues];

它将返回一个数组,然后您可以使用 NSSortDescriptor 对其进行排序。

于 2012-04-24T22:09:11.283 回答