How to fetch a range of items from the database - ios

How do I fetch, say, item 7 000 to 7 999 in my SQLite table with around 100 000 items?
The normal fetch returns to much to work with, and I rather fetch it little by little:
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
NSEntityDescription *entity = [NSEntityDescription
entityForName:#"Log"
inManagedObjectContext:context];
[fetchRequest setEntity:entity];
NSArray *fetchedObjects = [context executeFetchRequest:fetchRequest error:&err];
// here fetchedObjects holds around 100 000 rows
Is there a way to specify a range with in executeFetchRequest:fetchRequest?
Do I have to use the SQLite API?
Is it a good idea?

Use the fetchLimit and fetchOffset properties on NSFetchRequest to fetch an object in a selected range.
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
fetchRequest.fetchLimit = 1000;
fetchRequest.fetchOffset = 7000;
NSEntityDescription *entity = [NSEntityDescription
entityForName:#"Log"
inManagedObjectContext:context];
[fetchRequest setEntity:entity];
NSArray *fetchedObjects = [context executeFetchRequest:fetchRequest error:&err];

Related

Coredata is not updated

I wanted to update one record in my core data entity and I write code for it but the data is not updated .
There is Entity posts and it has data with id
i have to update the record for one particular id .
Here is function to update the record
-(void)updateDataInDB:(NSString*)withID WithDes:(NSString*)newData{
NSManagedObjectContext * context = [self getManagedContext];
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
NSEntityDescription *entity = [NSEntityDescription entityForName:#"News" inManagedObjectContext:context];
NSPredicate *predicate = [NSPredicate predicateWithFormat:#"postId == %#",withID];
[fetchRequest setPredicate:predicate];
[fetchRequest setFetchLimit:1];
[fetchRequest setEntity:entity];
NSError *error;
NSArray *arrResult = [context executeFetchRequest:fetchRequest error:&error];
if(arrResult.count>0){
NSManagedObject *news = [arrResult objectAtIndex:0];
[news setValue:newData forKey:#"fullDesc"];
}
[self saveContext];
}
Please Help if anything wrong
My core data contains duplicate records and i updated only first records so that the problem with update. After I updated all array records the code working fine.

Why CoreData is returning only 20 records?

I am using CoreData in my application. Everything is working fine except coredata is always returning max 20 records although i have more than 50 records. I have checked my code again and again but not finding the exact reason. I am also not using fetchLimit property. Kindly Help me.
Thanks.
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
NSEntityDescription *entity = [NSEntityDescription entityForName:entityName inManagedObjectContext:_manager.managedObjectContext];
[fetchRequest setEntity:entity];
NSSortDescriptor *sortDescriptor = nil;
if (key != nil) {
sortDescriptor = [[NSSortDescriptor alloc] initWithKey:key ascending:ascending];
NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
[fetchRequest setSortDescriptors:sortDescriptors];
}
NSError *error = nil;
NSMutableArray *array = [[_manager.managedObjectContext executeFetchRequest:fetchRequest error:&error] mutableCopy];
return array;
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
NSInteger rowCount = [context countForFetchRequest:fetchRequest error:&error];
fetchRequest.fetchLimit = rowCount;
NSArray *allItems = [context executeFetchRequest:fetchRequest error:&error];
Here rowCount will calculate actual count of all rows and you can set it as fetchLimit
Core Data returns 20 records by default. You can set records limit by using setFetchLimit of NSFetchRequest class.
NSFetchRequest* request = [[NSFetchRequest alloc] init];
[request setEntity:[...]];
[request setFetchLimit:50];

FetchRequest not updated with most recent record added to Core Data

Every time my app runs it generates data that is stored in a core data entity "Entity". The result of my fetch request does not update with this most recent data, except if I exit the app and relaunch it again. I thought the "shouldRefreshRefetchedObjects" property would fix this issue but apparently not. My current fetch request code is the following:
NSEntityDescription *entity = [NSEntityDescription entityForName:#"Entity" inManagedObjectContext:context];
NSSortDescriptor *descriptor = [[NSSortDescriptor alloc] initWithKey:#"date_time" ascending:YES];
NSArray *Descriptors = [NSArray arrayWithObject: descriptor];
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
[fetchRequest setShouldRefreshRefetchedObjects:YES];
[fetchRequest setEntity:entity];
[fetchRequest setSortDescriptors:Descriptors];
NSArray *historyDataArray = [context executeFetchRequest:fetchRequest error:Nil];

How to update fetched managed objects?

I'm having troubles in updating a specific record in my core data. What happens in my code is it does change the value but when I rerun the app it goes back to its original value. Why that happens?
NSManagedObjectContext *context = [self managedObjectContext];
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
NSEntityDescription *entity = [NSEntityDescription entityForName:#"Wish" inManagedObjectContext:context];
[fetchRequest setEntity:entity];
// Specify criteria for filtering which objects to fetch
NSPredicate *predicate = [NSPredicate predicateWithFormat:#"itemWish = %#", self.wishItemStr];
[fetchRequest setPredicate:predicate];
NSError *error = nil;
NSArray *fetchedObjects = [context executeFetchRequest:fetchRequest error:&error];
[fetchedObjects setValue:#"YES" forKeyPath:#"isAchieved"];
if (fetchedObjects == nil) {
NSLog(#"no fetched objects!");
}
You need to save the context.
[managedObjectContext save:&error];
I suggest you to read these very good tutorials and articles on objc.io.

How to fetch data from NSManaged object context

NSFetchRequest *fetchLLObjects = [[NSFetchRequest alloc] init];
[fetchLLObjects setEntity:[NSEntityDescription entityForName:#"CustomerOrder" inManagedObjectContext:self.managedObjectContext]];
[fetchLLObjects setIncludesPropertyValues:NO]; //only fetch the managedObjectID
NSError *error = nil;
NSArray *allObjects = [self.managedObjectContext executeFetchRequest:fetchLLObjects error:&error];
Here array is showing nil. But in database I could see that there are data. I don't know what might be the reason.
Please add your predicate in the fetchrequest
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
NSEntityDescription *entity = [NSEntityDescription entityForName:#"CustomerOrder"
[fetchRequest setPredicate:[NSPredicate predicateWithFormat:#"managedObjectID == %#", managedObjectID]] inManagedObjectContext:self.managedObjectContext];
[fetchRequest setEntity:entity];
NSArray *fetchedObjects = [self.managedObjectContext executeFetchRequest:fetchRequest error:nil];
Set following 2 properties and you are done.
fetchRequest.returnsDistinctResults = YES;
fetchRequest.resultType = NSDictionaryResultType;
Hope this helps.
Edit
NSFetchRequest *fetchRequest= [[NSFetchRequest alloc]init];
NSEntityDescription *entity = [NSEntityDescription entityForName:#"Songs" inManagedObjectContext:myManagedObjectContext];
//Take properties dictionary
NSDictionary *entityProperties = [entity propertiesByName];
[fetchRequest setEntity:entity];
[fetchRequest setReturnsDistinctResults:YES];
[fetchRequest setPropertiesToFetch:[NSArray arrayWithObject:[entityProperties objectForKey:#"song_type"]]];
NSArray * result = [myManagedObjectContext executeFetchRequest:fetchRequest error:nil];
You said: "But in database I could see that there are data."
I'm skeptical of that statement. I suspect that no CustomerOrder objects exist in the Core Data store. The only way to "see" the data inside the store is to turn off journaling mode and use 3rd party software to peak inside the .sqlite file.
Despite what others have said, your fetch request is fine. So double check your code where you insert objects into the store and save to the context.

Resources