Search code examples
swiftvariablesconstantsread-eval-print-loop

let and var Invalid redeclaration of const in Swift REPL


In Swift REPL I can assign a constant with let, but why can I modify it later using var?

let name = "al"

var name = "bob"

Swift is not complaining here, but wasn't name a constant?


Solution

  • Redeclaring a variable (in the same scope) is not valid in Swift:

    $ cat test.swift 
    let name = "al"
    var name = "bob"
    
    $ swiftc test.swift 
    test.swift:2:5: error: invalid redeclaration of 'name'
    var name = "bob"
        ^
    test.swift:1:5: note: 'name' previously declared here
    let name = "al"
        ^
    

    However, the Swift REPL behaves differently:

    $ swift
    Welcome to Apple Swift version 3.1 (swiftlang-802.0.53 clang-802.0.42). Type :help for assistance.
      1> let name = "al" 
    name: String = "al"
      2> var name = "bob"
    name: String = "bob"
    

    This is intentional, as explained in Redefining Everything with the Swift REPL:

    ... but in the REPL interactive environment it’s useful to be able to easily make changes. The REPL was specifically designed with this kind of convenience in mind ...

    ... The newer definition replaces the existing definition for all subsequent references


    Note: You have to enter the lines separately. If you copy those two lines into the paste buffer, start the REPL and paste them with CmdV then the result is

    $ swift
    Welcome to Apple Swift version 3.1 (swiftlang-802.0.53 clang-802.0.42). Type :help for assistance.
      1> let name = "al" 
      2. var name = "bob"
    error: repl.swift:2:5: error: invalid redeclaration of 'name'
    var name = "bob"
        ^
    

    Apparently the two statements are now evaluated in the same scope (the second line has a continuation prompt) and produce an error. The same happens with both statements in a single line:

    $ swift
    Welcome to Apple Swift version 3.1 (swiftlang-802.0.53 clang-802.0.42). Type :help for assistance.
      1> let name = "al" ; var name = "bob"
    error: repl.swift:1:23: error: invalid redeclaration of 'name'
    let name = "al" ; var name = "bob"
                          ^