-1

I tried to perform simple mathematical calculations based on input from several textfields. When one field is not filled in, I would like to continue the calculation for other fields. However, this does not work with my use of the (inappropriate?) guard statement.

Put simply:

If field1 is filled in, perform calculation (i.e. multiply that amount by 0.5) and store the result.

If field2 is filled in, perform calculation (i.e. multiply that amount by 0.2) and store the result.

etc.

As an absolute beginner, I tried this:

@IBAction func calculate(_ sender: Any) {
    //amount 1
    guard let amount1 = textField1.text else{
        return}
    guard let amount1double = Double(amount1) else{
        return}

    var amt1 = amount1double
    amt1 = amt1 * 0.5

    //amount 2
    guard let amount2 = textField2.text else{
        return }

    guard let amount2double = Double(amount2) else{
        return }

    var amt2 = amount2double
    amt2 = amt2 * 0.2
}

The above code will stop if textField1 is not filled in. However I want the code to continue to calculate amount2 if textField1 is empty.

I read about if let statements to maybe continue with the rest of the code after a nil in the texfField, however I could not make it work. Furthermore I understand this will only allow me to access that value within that block.

The goal is to ultimately get the highest / maximum amount from all calculated amounts, if available.

mfaani
  • 33,269
  • 19
  • 164
  • 293
P. Anda
  • 1
  • 2
  • you can try splitting them into 2 methods – guenis Jul 09 '17 at 11:04
  • See [here](https://stackoverflow.com/a/39263210/5175709). You've spotted 2 differences between `guard` and `if let` 1. `guard` will **exit scope early** 2. using `if let` you can't create an external variable. Yet if you use `guard` you are *creating* a variable. Your problem is you need some of the features of `if let` and some of the features of `guard` :/ Having that said there are multiple ways of solving the problem I think [Optimus's](https://stackoverflow.com/a/44996893/5175709) solution is a good one. – mfaani Jul 09 '17 at 17:48

3 Answers3

1

I tried to solve your problem using if-let. Check below code.

var amt1 : Double = 0.0
        if let amount1 = textfield1.text{
            if let amount1InDouble = Double(amount1){
                amt1 = amount1InDouble
                amt1 = amt1 * 0.5
            }
        }

        var amt2 : Double = 0.0
        if let amount2 = textfield2.text{
            if let amount2InDouble = Double(amount2){
                amt2 = amount2InDouble
                amt2 = amt2 * 0.2
            }
        }
pkc456
  • 8,350
  • 38
  • 53
  • 109
0

UPDATE

You don't need to use guard or if-let then. You can just use let with default value.

@IBAction func calculate(_ sender: Any) {
    let amount1double = Double(textField1.text ?? "") ?? 0 // 0 is default value, Change it to whatever you want.
    let amount2double = Double(textField2.text ?? "") ?? 0 // 0 is default value, Change it to whatever you want.

    var amt1 = amount1double
    amt1 = amt1 * 0.5

    var amt2 = amount2double
    amt2 = amt2 * 0.5
}

Using if let

@IBAction func calculate(_ sender: Any) {    
    if let amount1 = textField1.text,
        let amount2 = textField2.text,
        let amount1double = Double(amount1),
        let amount2double = Double(amount2) {

        var amt1 = amount1double
        amt1 = amt1 * 0.5

        var amt2 = amount2double
        amt2 = amt2 * 0.5
    }
}

Using guard

@IBAction func calculate(_ sender: Any) {    
    guard let amount1 = textField1.text,
        let amount2 = textField2.text,
        let amount1double = Double(amount1),
        let amount2double = Double(amount2)  else {
        return
    }

    var amt1 = amount1double
    amt1 = amt1 * 0.5

    var amt2 = amount2double
    amt2 = amt2 * 0.5
}
Bilal
  • 18,478
  • 8
  • 57
  • 72
  • User's goal is `to ultimately get the highest / maximum amount from all calculated amounts`. You declared `amt1` and `amt2` inside the if-let, thus not accessible to get the max amount. – pkc456 Jul 09 '17 at 11:03
  • You're answer only works if both values textFields have an integer. It doesn't work if only one of the textFields has a value. If one textField is empty the OP still wants to have a calculated value. – mfaani Jul 09 '17 at 17:54
  • in that case you don't need to use `guard` or `if-let`. Just use `let` with default value. – Bilal Jul 10 '17 at 03:38
0

Hi you can do like this:

@IBAction func calculate(_ sender: Any) {
    //amount 1
    let amount1double = calculateAmountTxt1()
    //amount 2
    let amount2double = calculateAmountTxt2()

    var amt1 = amount1double
    amt1 = amt1 * 0.5

    var amt2 = amount2double
    amt2 = amt2 * 0.2
}

func calculateAmountTxt1()->CGFloat{
     //amount 1
    guard let amount1 = textField1.text, let amount1double = Double(amount1)else {
       return 0
    }
    return amount1double
}

func calculateAmountTxt2()->CGFloat{
    //amount 2
    guard let let amount2 = textField2.text,let amount2double = Double(amount2)else {
       return 0
    }
    return amount2double
}
mfaani
  • 33,269
  • 19
  • 164
  • 293
Optimus
  • 800
  • 5
  • 16