Remove Duplicate Structs in Array Based on Struct Property in Swift

Remove duplicated in a Struct Array

First off, I tried making a sample in my PlayGround.

  1. Conform your model model to the protocal Equatable, like so:

    struct Car: Equatable {

    var modelName = String()
    var manufacturer = String()

    init(modelName: String, manufacturer: String) {
    self.modelName = modelName
    self.manufacturer = manufacturer
    }

    static func == (lhs: Car, rhs: Car) -> Bool {
    return lhs.modelName == rhs.modelName
    }
    }

In the code above, we're assuming that the modelName is the primary key of your model.


  1. Now make a function that enumerates your data source and returns a new data source after checking the element one by one, like so:

    // returns unique array

    func unique(cars: [Car]) -> [Car] {

    var uniqueCars = [Car]()

    for car in cars {
    if !uniqueCars.contains(car) {
    uniqueCars.append(car)
    }
    }

    return uniqueCars
    }

Finally, you now have the function to generate a new unique data source.

Example:

// Variable

var cars = [Car]()

// Adding data models to data source

let car1 = Car(modelName: "Kia Picanto", manufacturer: "Kia")
let car2 = Car(modelName: "Honda XX", manufacturer: "Honda")
let car3 = Car(modelName: "Honda XX", manufacturer: "Honda")

cars.append(car1)
cars.append(car2)
cars.append(car3)

// Now contains only two elements.
let uniqueCars = unique(cars: cars)

remove duplicates from struct

You can filter this way after you finish appending to the array.

    var unique = [WheelBrand]()
for arrValue in itemWheelBrand {
if !unique.contains(where: { $0.id == arrValue.id }) {
unique.append(arrValue)
}
}

Removing duplicate elements from an array in Swift

You can roll your own, e.g. like this:

func unique<S : Sequence, T : Hashable>(source: S) -> [T] where S.Iterator.Element == T {
var buffer = [T]()
var added = Set<T>()
for elem in source {
if !added.contains(elem) {
buffer.append(elem)
added.insert(elem)
}
}
return buffer
}

let vals = [1, 4, 2, 2, 6, 24, 15, 2, 60, 15, 6]
let uniqueVals = uniq(vals) // [1, 4, 2, 6, 24, 15, 60]

And as an extension for Array:

extension Array where Element: Hashable {
func uniqued() -> Array {
var buffer = Array()
var added = Set<Element>()
for elem in self {
if !added.contains(elem) {
buffer.append(elem)
added.insert(elem)
}
}
return buffer
}
}

Or more elegantly (Swift 4/5):

extension Sequence where Element: Hashable {
func uniqued() -> [Element] {
var set = Set<Element>()
return filter { set.insert($0).inserted }
}
}

Which would be used:

[1,2,4,2,1].uniqued()  // => [1,2,4]

Remove objects with duplicate properties from Swift array

I am going to suggest 2 solutions.

Both approaches will need Post to be Hashable and Equatable

Conforming Post to Hashable and Equatable

Here I am assuming your Post struct (or class) has an id property of type String.

struct Post: Hashable, Equatable {
let id: String
var hashValue: Int { get { return id.hashValue } }
}

func ==(left:Post, right:Post) -> Bool {
return left.id == right.id
}

Solution 1 (losing the original order)

To remove duplicated you can use a Set

let uniquePosts = Array(Set(posts))

Solution 2 (preserving the order)

var alreadyThere = Set<Post>()
let uniquePosts = posts.flatMap { (post) -> Post? in
guard !alreadyThere.contains(post) else { return nil }
alreadyThere.insert(post)
return post
}

Creating an array of struct without duplicates

A solution is to shuffle the surname, age and email arrays separately to get a random but unique order.

let nameA  = ["Tim", "Mike", "Stan"]
let surnameA = ["Burk", "Sims", "Stoch"]
let ageA = ["12", "30", "25"]
let emailA = ["one@live.com", "two@gmail.com", "three@outlook.com"]

func createRandomHuman() -> [Human] {
let shuffledSurnameA = surnameA.shuffled()
let shuffledAgeA = ageA.shuffled()
let shuffledEmailA = emailA.shuffled()
var humans: [Human] = []
for i in 0..<nameA.count {
let human = Human(name: nameA[i],
surname: shuffledSurnameA[i],
age: shuffledAgeA[i],
email: shuffledEmailA[i])
humans.append(human)
}
return humans
}

let arrayOfHumans = createRandomHuman()

Another way is to shuffle the indices

func createRandomHuman() -> [Human] {
let indices = nameA.indices
let shuffledIndices = (0..<3).map{ _ in indices.shuffled()}
var humans: [Human] = []
for i in 0..<nameA.count {
let human = Human(name: nameA[i],
surname: surnameA[shuffledIndices[0][i]],
age: ageA[shuffledIndices[1][i]],
email: emailA[shuffledIndices[2][i]])
humans.append(human)
}
return humans
}

Swift: Removing duplicate objects from array with a UUID

So I'm guessing what you want to do is to remove those duplicates?

Then write a function that removes the duplicates based on the name of the movie (which I'm guessing is unique) and use it to filter.

func removeDup(movies: [MovieSearch]) -> [MovieSearch] {
var uniqueMovies = Set<String>()
var moviesWithoutDups = [MovieSearch]()

for movie in movies {
if !uniqueMovies.contains(movie.name) {
moviesWithoutDups.append(movie)
uniqueMovies.insert(movie.name)
}
}
return moviesWithoutDups
}

Then use the function:

movies = removeDup(movies: movies)


Related Topics



Leave a reply



Submit