Sort an array of objects, following the order of another array that has a value of the objects of the first array - swift

How could I sort an array of objects taking into account another array?
Example:
let sortArray = [90, 1000, 4520]
let notSortArrayObject = [ { id: 4520, value: 4 }, {id: 1000, value: 2}, {id: 90, value:10} ]
So I want an array equal notSortArrayObject but sortered by sortArray value
let sortArrayObject =[{id: 90, value:10} , {id: 1000, value: 2}, { id: 4520, value: 4 }]

Here's an approach. For each number in the "guide" array, find a match in the not sorted and add it to the sortedObjectArray. Note that this ignores any values which don't have matches in the other array.
var sortedObjectArray: [Object] = [] // whatever your object type is
for num in sortArray {
if let match = notSortArrayObject.first(where: {$0.id == num}) {
sortedObjectArray.append(match)
}
}
If you just want to sort by the id in ascending order, it's much simpler:
let sorted = notSortArrayObject.sorted(by: {$0.id < $1.id})

I noticed that sortArray is already sorted - you could just sort notSortArrayObject by id, but I assume that's not the point of what you're looking for.
So, let's say that sortArray = [1000, 4520, 90] (random order), to make things more interesting.
You can iterate through sortArray and append the values that match the id to sortArrayObject.
// To store the result
var sortArrayObject = [MyObject]()
// Iterate through the elements that contain the required sequence
sortArray.forEach { element in
// Add only the objects (only one) that match the element
sortArrayObject += notSortArrayObject.filter { $0.id == element }
}

Related

filtering an array and counting the number of elements

I am trying to count the number of items in an array which correspond to a particular attribute.
func subCount() {
let arr = subDS.subFolders // array
var counts: [String: Int] = [:]
arr.forEach { counts[$0.parentFolder!, default: 0] += 1 }
print(Array(counts.values))
}
when the code above is executed, if the count is zero it does not appear in the array. Also the order of the array formed in an incorrect order.
You can use filter method
for example :
var filterArray = subDS.subFolders.filter { $0. parentFolder == 0 }
let count = filterArray.count
The first $0 is from the filter and it represents each subFolders.

How to sort a dictionary based on keys and sort its respective values in Swift

I have a dictionary with string as key and an array of int as values , i need to sort the dictionary based on keys and the array value should also be sorted.
var dicNumArray : Dictionary<String , [Int]> = ["q":[4,3,2,1,5],"a":[2,3,4,5,5],"s":[123,123,132,43,4],"t":[0,88,66,542,321]]
The result i need is the dictionary itself where it is sorted by keys and respective values are also sorted.
You can apply sorted to each the value of the key-value pair of a dictionary using mapValues
And then, you can just use sorted with a predicate comparing the keys of the dictionary.
let result = dicNumArray.mapValues { $0.sorted() }
.sorted { $0.key < $1.key }
This will return an array of key-value pair tuples.
Since, dictionaries can't be trusted with order, working with an array of the key-value pairs is the next best approach.
We can use .key and .value to get the respective values.
result.first?.key // First key
result.first?.value // First value
Dictionaries don't have an order in Swift. Having said that, you can do something like this
var dicNumArray : Dictionary<String , [Int]> = ["q":[4,3,2,1,5],"a":[2,3,4,5,5],"s":[123,123,132,43,4],"t":[0,88,66,542,321]]
func sortData() {
for (key, value) in dicNumArray {
dicNumArray[key] = value.sorted(by: { $0 < $1 })
}
}
sortData()
This will sort array for each key. Once that's done, you can do something like
let keys = Array(dicNumArray.keys).sorted(by: { $0 < $1 })
This will give you a sorted array of dictionary keys. You can test it as follows
TEST
for key in keys {
print("\(key): \(dicNumArray[key]!)")
}
OUTPUT
a: [2, 3, 4, 5, 5]
q: [1, 2, 3, 4, 5]
s: [4, 43, 123, 123, 132]
t: [0, 66, 88, 321, 542]
you can apply sort key , then map to sorted by array
let sortedKeysAndValues = dicNumArray.sorted(by: {$0.0 < $1.0}).map { [$0.key:$0.value.sorted(by: <)]}.flatMap({$0})

How to sort dictionary by value?

My dictionary like this:
var items = [Int: [String]]()
var itemsResult = [Int: [String]]()
itmesResult stores the data downloaded from server.
and pass the data to items use of items = itmesResult
the value has 3 elements like ["Apple","/image/apple.png","29"]
and I want to sort the dictionary by first value which is Apple.
for (k,v) in (itemsResult.sorted(by: { $0.value[0] < $1.value[0] })) {
items[k] = v
}
The result of above code is not my expectation.
I would like to sort it alphabetically how can I do this?
Edit:
origin:
1:["Apple","/image/apple.png","29"]
2:["AAA","/image/aaa.png","29"]
3:["Banana","/image/banana.png","29"]
sorted:
2:["AAA","/image/aaa.png","29"]
1:["Apple","/image/apple.png","29"]
3:["Banana","/image/banana.png","29"]
I would like to sort it by first value.
So if I take your example, this does the trick:
var items = [Int: [String]]()
items[0] = ["Apple","/image/apple.png","29"]
items[1] = ["AAA","/image/aaa.png","29"]
items[2] = ["Banana","/image/banana.png","29"]
let itemResult = items.sorted { (first: (key: Int, value: [String]), second: (key: Int, value: [String])) -> Bool in
return first.value.first! < second.value.first!
}
print (itemResult)
The right thing to do is to use objects of course, and note that I'm not null checking the "first" object in each array, but this is not a problem to change.
Let me know if this is what you were looking for, the output is:
[(1, ["AAA", "/image/aaa.png", "29"]), (0, ["Apple", "/image/apple.png", "29"]), (2, ["Banana", "/image/banana.png", "29"])]
EDIT:
Also note, that this case doesn't actually "sort" the dictionary, because a dictionary is by definition not sorted, this creates an array of key-value objects sorted using the array indexes
Instead of saving these variable into an array of arrays, make them an array of dictionaries.
You can do this like so:
var dictionaries:[Dictionary<String, String>] = []
for item in items {
let dictionary = {"name": item[0], "url": item[1], "id" : item[2]}
dictionaries.append(dictionary)
}
You can get your sorted list of dictionaries like this:
dictionaries.sorted(by: { $0["name"] < $1["name"] })

Split dictionaries in two array and sort the dictionary by value swift

1) this is first step : I'm asking how to make this dictionary in order by value.
2)second step: I want to split this dictionary in two array, one for value and one for keys thanks
["fruit": 1, "vegie": 13, "money": 46, "Canada": 219, "cash": 1, "lola": 1, "tv": 2, "bed": 1, "sofa": 1]
I did something like that but I want to split in two arrays now
let byValue = {
(elem1:(key: String, val: Int), elem2:(key: String, val: Int))->Bool in
if elem1.val < elem2.val {
return true
} else {
return false
}
}
let sortedDict = dict.sort(byValue)
Assuming that the part 1 of your question is done as you said in your last edit, here is how to have...
The keys:
let keys = sortedDict.map { $0.0 }
And the values:
let values = sortedDict.map { $0.1 }

Sorting an array of month chronologicaly in swift

Here is my array that i wan't to sort:
["Septembre", "Novembre", "Août", "Mars", "Décembre", "Octobre", "Juillet", "Avril", "Juin", "Février", "Janvier", "Mai"]
How can i sort this array?
You will need to make a Dictionary with key as the month name in String and value in int corresponding to the order in which the months come in the year. Then using this library http://www.dollarswift.org/#keys-keys you can
let monthsDict = ["feb": 1, "mar": 2, "jan": 0]
var months = $.keys(monthsDict)
months.sort {
monthsDict[$0] < monthsDict[$1]
}
If you want it reversed you can just flip the equality operator
months.sort {
monthsDict[$0] > monthsDict[$1]
}