Reputation: 8547
I am having a CoreData structure. It is working fine for me. Now I am trying to do an interesting FetchRequest
, however I am struggeling to find the correct predicate
.
I am having two ententies, Person
and Venues
. A person can be connected to many venues, but only once to the same venue
. And other way around.
I have created a mapping table, which saves the person
and venue
as relationships. Everything is working fine here. I even implemented the inverse
relationship.
In the picture left is my venue. I want to Fetch all persons
based on a current venue, where there is NO Mapping created already.
My approach was to use pk_venue
, which gives me a set of PersonVenueMapping
. However, how can I only use the persons
of that Set.
fetch.predicate = NSPredicate(format: "NOT (person IN %@)", venue!.pk_venue[HELP])
I came up with that Predicate. However, how can I access the persons of that set? I would need a array/ set of only the persons
, that are connected to that current object.
Edit: Just to give you example.
Person: Max, Leon, Henry
Venue: Venue1, Venue2, Venue 3, Venue 4
PersonVenueMapping: Max <-> Venue1
Now when I select Max
, I want Venue2
& Venue3
& Venue4
Thanks in advance
Upvotes: 1
Views: 153
Reputation: 77661
Your model looks very much like a normalised database type model. CoreData is not a database and so some of the requirements of modelling data are more flexible when using it. For instance many to many
relationships are possible (and encouraged).
Create your model in this way...
Person
------
name: String
------
assignedVenues: Many relationship to `venue` type
Now every relationship has an inverse property, so...
Venue
------
name: String
------
managers: Many relationship to `Person` type
Now you can go from Max to his assigned venues just by doing...
let selectedPerson = // fetch Max from CoreData
let venues = selectedPerson.assignedVenues
Equally you can go from a venue to find all the people managing it...
let someVenue = // fetch venue from CoreData
let managers = someVenue.managers
To satisfy your question of finding all venues that Max is not managing you can now do a query like...
let selectedPerson = //fetch Max
let predicate = NSPredicate(format:"NONE managers == %@", selectedPerson) // Its been a long time since I did CoreData so forgive me if this syntax isnt correct but the idea is correct. :D
You can now use that predicate to get all venues
where max is NOT one of the managers of the venue.
By removing the "mapping" that is required in something like SQLite etc... you can make things much simpler for yourself.
Upvotes: 1
Reputation: 21536
I am confused as to whether you are fetching persons with no mapping to a given venue, or venues with no mapping to a given person. I’ll assume the latter.
Your fetch request will therefore be for the entity Venue. Let’s call the selected Person selectedPerson
. The following predicate should return only those Venues that have no mapping to selectedPerson
:
NSPredicate(format:”SUBQUERY(pk_venue, $M, $M.person == %@).@count == 0”, selectedPerson)
or in natural language “fetch Venues for which the count of mappings ($M), with person
equal to the selected person, is zero”.
Upvotes: 1