简体   繁体   中英

Error When Converting JSON String To Number Using Swift

I have a basic question to convert string to number in Swift. I found a good stack overflow question that helps me convert a JSON string to a number, but I get an error when I try to add or subtract the values.

I am sure I am missing something obvious!

Phil

Error: Referencing operator function '-' on 'BinaryInteger' requires that 'NSNumber' conform to 'BinaryInteger'

func red2G()->String {
        let numberFormatter = NumberFormatter()
        
        // Prev Close
        let number1  = numberFormatter.number(from: pricesAlpha?.globalQuote.prevClose ?? "0.000")
        if let final1 = number1?.floatValue {
        print("Returned number is " + String(format: "%.2f", final1))
        }
        
        // Open
        let number2  = numberFormatter.number(from: pricesAlpha?.globalQuote.open ?? "0.000")
        if let final2 = number2?.floatValue {
        print("Returned number is " + String(format: "%.2f", final2))
        }
        
        // Price
        let number3  = numberFormatter.number(from: pricesAlpha?.globalQuote.price ?? "0.000")
        if let final3 = number3?.floatValue {
        print("Returned number is " + String(format: "%.2f", final3))
        }
        
        return String(number3-number2)
     }

I simplified the function based on the proposed answer:

    func load(symbolName:String) {
        self.symbolName = symbolName
    }
    
    func red2G()->String {
        let numberFormatter = NumberFormatter()
        
        // Prev Close
        let prevClose  = numberFormatter.number(from: pricesAlpha?.globalQuote.prevClose ?? "0.000")?.floatValue
        
        // Open
        let openPrice  = numberFormatter.number(from: pricesAlpha?.globalQuote.open ?? "0.000")?.floatValue
        
        // Price
        let currentPrice  = numberFormatter.number(from: pricesAlpha?.globalQuote.price ?? "0.000")?.floatValue
        
        return String((openPrice ?? 0.00) - (prevClose ?? 0.00) - (currentPrice ?? 0.00))
}

The values are based on this JSON Dictionary

struct GlobalQuote: Codable {
    let globalQuote: PriceAlpha
    
    enum CodingKeys : String, CodingKey {
        case globalQuote = "Global Quote"
    }
}

struct PriceAlpha: Codable {
    let symbol: String
    let open: String
    let high: String
    let low: String
    let price: String
    let volume: String
    let tradingDay: String
    let prevClose: String
    let change: String
    let pctChange: String
    
    enum CodingKeys : String, CodingKey {
        case symbol = "01. symbol"
        case open = "02. open"
        case high = "03. high"
        case low = "04. low"
        case price = "05. price"
        case volume = "06. volume"
        case tradingDay = "07. latest trading day"
        case prevClose = "08. previous close"
        case change = "09. change"
        case pctChange = "10. change percent"
    }
}

NSNumber is a object wrapper around an actual integer or float or whatever. You see in your code where you call floatValue ? That gets an actual number that you can do math with. Keep final3 and final2 around outside of their if statements and do the math on that.

That said, you should almost certainly implement custom decoding and encoding in PriceAlpha so that the struct already contains values in the correct semantic type (eg Float ) instead of String . But for financial information, you'll actually want Decimal , not Float .

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM