1

I have a custom class called Place with 3 properties:

  • Name (String)
  • Category (String)
  • GeoPoint (CLLocationCoordinate2D)

I have an array of type [Place] of 100 objects and I want to check if there are duplicates on the GeoPoint property (just on this one).

How can I check duplicates of a specific property in an array of custom objects?

Thanks!

Wyetro
  • 8,439
  • 9
  • 46
  • 64
FS.O6
  • 1,394
  • 2
  • 20
  • 42
  • 2
    Possible duplicate of [Find Duplicate Elements In Array Using Swift](http://stackoverflow.com/questions/29727618/find-duplicate-elements-in-array-using-swift) – Ahmad F Nov 17 '16 at 07:57
  • You could loop through the array, make a dictionary for each GeoPoint with the GeoPoint being the key and the count being the value and then check all the values to see if there's one that's greater than zero. – Wyetro Nov 17 '16 at 08:00
  • @WMios I don't undersatnd – FS.O6 Nov 17 '16 at 08:01
  • 1
    Make it become a set then revert back to array is fastest way i suppose – Tj3n Nov 17 '16 at 08:07
  • @FS.O6, see my answer if you don't understand my comment. – Wyetro Nov 17 '16 at 08:08

2 Answers2

2

Although the accepted answer is good, I'd like to chip in.

There are two more ways to achieve what you want, and they both benefit from functionalities provided by SDK.

1 - Use Sets as Tj3n mentioned in a comment. To achieve this you would need to make your Place conform to Hashable protocol.

class Place : Hashable {
    var name = ""
    var category = ""
    var geoPoint: CLLocationCoordinate2D = CLLocationCoordinate2D()

    var hashValue: Int {
        get {
            return geoPoint.longitude.hashValue &+ geoPoint.latitude.hashValue
        }
    }
}

func ==(lhs: Place, rhs: Place) -> Bool {
    return lhs.geoPoint.latitude == rhs.geoPoint.latitude && lhs.geoPoint.longitude == rhs.geoPoint.longitude
}

The &+ operator in hashValue means "add, and don't crash at overflow". Using it is as straightforward as it can - let set = Set(yourArrayOfPlaces) - the set will contain only unique, in regard to geoPoint, places.

2 - Use KVC. While this is more of an Objective-C world, I find it a useful tool. To achieve this, you'd need to make Place inherit from NSObject. Then getting an array of unique places can be reduced to this one line :

let uniquePlaces = (yourPlacesArray as NSArray).value(forKeyPath: "@distinctUnionOfObjects.geoPoint")
Losiowaty
  • 7,911
  • 2
  • 32
  • 47
1

You can do something like this:

var dict : [String : Int] = [:]

for place in arr {
    if dict[place.GeoPoint] != nil {  // Not in dictionary
        if dict[place.GeoPoint] >= 1 { // If already there
            return true // Duplicate
        } else {
            dict[place.GeoPoint]! += 1 // Increment instance
        }
    } else {
        dict[place.GeoPoint] = 0 // Put in dictionary
    }
}

return false // No duplicates

Where you loop through a [Place] array and check to see how many have the same GeoPoint. Then check to see if there's one there more than once.

Wyetro
  • 8,439
  • 9
  • 46
  • 64