1

I was translating this script here to Swift: https://stackoverflow.com/a/3758880/2430555

The error: binary operator '<' cannot be applied to operands of type '()' and 'Int'

But I am stuck in the part below, this is not compiling because \= is not returning the value, instead it's returning (). Any idea what this could be?

var b: Int64 = Int64(1e3)
let bb = ((b/=1000) < 999_950)

Thank you all.

Pedro Paulo Amorim
  • 1,838
  • 2
  • 27
  • 50

2 Answers2

2

(b/=1000) is a function that returns a void ('aka' () ).

You cant compare a Void and a number (by default)

You can refactor it to:

var b: Int64 = Int64(1e3)
b/=1000
let bb = ( b < 999_950)

Based on the evidence in the other answer by yourself, you are looking for byte converter. You can achieve it like:

func convertBitrateToHumanReadable(bytes: Int64) -> String { ByteCountFormatter().string(fromByteCount: bytes) }

Previously other solution:

You can implement a custom operator for this: (I'm not fan of using this. see @Alexander - Reinstate Monica comment)

infix operator /=> : MultiplicationPrecedence
precedencegroup MultiplicationPrecedence {
  associativity: left
  higherThan: AdditionPrecedence
}

public func /=><T: Numeric>(lhs: inout T, rhs: T) -> T{
    lhs = lhs + rhs
    return lhs
}

Now you can use it like:

let bb = ( b/=>1000 < 999_950)
Community
  • 1
  • 1
Mojtaba Hosseini
  • 95,414
  • 31
  • 268
  • 278
0

Based on @Mojtaba Hosseini answer, I build this (still not working as expected):

public func humanReadableByteCountSI(_ bytes: Int64) -> String {
    let s: String = bytes < 0 ? "-" : ""
    var b: Int64 = bytes == Int64.min ? Int64.max : abs(bytes)
    let d: Int64 = Int64(1e3)

    let div: () -> Int64 = {
        b/=1000
        return b
    }

    return b < 1000 ? String(format: "%i B", bytes)
        : b < 999_950 ? String(format: "%s%.1f kB", s, Float(b / d))
        : div() < 999_950 ? String(format: "%s%.1f MB", s, Float(b / d))
        : div() < 999_950 ? String(format: "%s%.1f GB", s, Float(b / d))
        : div() < 999_950 ? String(format: "%s%.1f TB", s, Float(b / d))
        : div() < 999_950 ? String(format: "%s%.1f PB", s, Float(b / d))
        : String(format: "%s%.1f EB", s, Float(b / Int64(1e6)))
}
Pedro Paulo Amorim
  • 1,838
  • 2
  • 27
  • 50
  • Oh I have a very simpler solution for this. [Check this out](https://stackoverflow.com/a/56237217/5623035) – Mojtaba Hosseini Dec 06 '19 at 18:52
  • 1
    Before you start implementing something like this, check that something like this exists. In this case, yes, it does: ByteCountFormatter – Alexander Dec 06 '19 at 18:53
  • `var b: Int64 = bytes == Int64.min ? Int64.max : abs(bytes)` what ಠ_ಠ – Alexander Dec 06 '19 at 18:56
  • You also have a critical memory error in `String(format: "%s%.1f B", bytes)`, because you forgot the `s` parameter. The `bytes` is read as a string (undefined behaviour), followed by whatever else in memory, read as a float (also undefined behaviour). Such is the risk of using legacy C/ObjC APIs. – Alexander Dec 06 '19 at 18:58
  • @MojtabaHosseini I simply implemented this for the challenge of converting that Java code to Swift. – Pedro Paulo Amorim Dec 06 '19 at 19:19
  • @Alexander-ReinstateMonica I Hope I got it sorted. – Pedro Paulo Amorim Dec 06 '19 at 19:24