0

I have the following json array

[
  {
    "name" : "v1",
    "available" : 1
  },
  {
    "name" : "v2",
    "available" : 3
  },
  {
    "name" : "v3",
    "available" : 2
  },
  {
    "name" : "v4",
    "available" : 3
  },
  {
    "name" : "v5",
    "available" : 3
  },
  {
    "name" : "v6",
    "available" : 1
  },
  {
    "name" : "v7",
    "available" : 2
  }
]

the available show some numbers which means: 1 and 3 is ok 2 is not ok

How can I order that json array by available value, showing first the 1 and 3 values and the last the value with 2. The result list should looks like this:

[
  {
    "name" : "v1",
    "available" : 1
  },
  {
    "name" : "v6",
    "available" : 1
  },
  {
    "name" : "v2",
    "available" : 3
  },
  {
    "name" : "v4",
    "available" : 3
  },
  {
    "name" : "v5",
    "available" : 3
  },
  {
    "name" : "v3",
    "available" : 2
  },
  {
    "name" : "v7",
    "available" : 2
  }
]

How can I do that?

Note: I use swiftyJson

This is my code:

sortArrayOddsBeforeEvens(array: json_array)

func sortArrayOddsBeforeEvens(array: JSON){
  let odds = array.filter{ $0.1["available"].intValue % 2 != 0 }
  let evens = array.filter{ $0.1["available"].intValue % 2 == 0 }
  print(odds)
  print(evens)
}

How can I return that as JSON?

2
  • create custom element and sort this after append Commented Oct 29, 2018 at 20:07
  • can you write a piece of code? Commented Oct 29, 2018 at 20:11

2 Answers 2

1

You are going to sort the array by two criteria.

Suggestion aka usual algorithm: First sort by odd/even, if both values are equal sort by the integer value.

let array = [["name" : "v1", "available" : 1],["name" : "v6", "available" : 1],["name" : "v2", "available" : 3],["name" : "v4", "available" : 3],["name" : "v5", "available" : 3],["name" : "v3", "available" : 2],["name" : "v7", "available" : 2]]

let sortedArray = array.sorted { (d1, d2) -> Bool in
    let avail1 = d1["available"] as! Int
    let avail2 = d2["available"] as! Int
    let compareOddity = avail1 % 2 == 0 && avail2 % 2 != 0
    if compareOddity { return !compareOddity }
    return avail1 < avail2
}

print(sortedArray)

Two avoid ugly boilerplate code drop SwiftyJSON and use Decodable to decode the JSON into structs.
The code will look much cleaner (and is more efficient)

let sortedArray = array.sorted { (d1, d2) -> Bool in
    let compareOddity = d1.available % 2 == 0 && d2.available % 2 != 0
    if compareOddity { return !compareOddity }
    return d1.available < d2.available
}
Sign up to request clarification or add additional context in comments.

1 Comment

Clever approach. (Voted)
0
var array: [Int] = [1, 3, 2, 2, 1, 3, 3, 1, 2, 1, 3, 2, 2, 1]
array.filter({ return $0 != 2 }) + array.filter({ return $0 == 2})

Basically the logic is same.

let data = """
[
{ "name" : "v1", "available" : 1 },
{ "name" : "v2", "available" : 3 },
{ "name" : "v3", "available" : 2 },
{ "name" : "v4", "available" : 3 },
{ "name" : "v5", "available" : 3 },
{ "name" : "v6", "available" : 1 },
{ "name" : "v7", "available" : 2 }]
""".data(using: .utf8)!

let array = JSON(data).arrayValue
let result = array.filter({ return $0["available"].intValue != 2}) + array.filter({ return $0["available"].intValue == 2})

6 Comments

I need with json array my friend
Not much difference in the logic.
Your code works great if the values are in range 1...3 but it will fail if there are other values.
@vadian Seems like there are only 3 cases?
All @Ryan has to do to make this work for all values is change those filter conditions into return $0 % 2 == 0 for evens, and return $0 % 2 == 1 for odds.
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.