Leading zeros for Int in Swift
Solution 1
Assuming you want a field length of 2 with leading zeros you'd do this:
import Foundation
for myInt in 1 ... 3 {
print(String(format: "%02d", myInt))
}
output:
01 02 03
This requires import Foundation
so technically it is not a part of the Swift language but a capability provided by the Foundation
framework. Note that both import UIKit
and import Cocoa
include Foundation
so it isn't necessary to import it again if you've already imported Cocoa
or UIKit
.
The format string can specify the format of multiple items. For instance, if you are trying to format 3
hours, 15
minutes and 7
seconds into 03:15:07
you could do it like this:
let hours = 3
let minutes = 15
let seconds = 7
print(String(format: "%02d:%02d:%02d", hours, minutes, seconds))
output:
03:15:07
Solution 2
With Swift 5, you may choose one of the three examples shown below in order to solve your problem.
#1. Using String
's init(format:_:)
initializer
Foundation
provides Swift String
a init(format:_:)
initializer. init(format:_:)
has the following declaration:
init(format: String, _ arguments: CVarArg...)
Returns a
String
object initialized by using a given format string as a template into which the remaining argument values are substituted.
The following Playground code shows how to create a String
formatted from Int
with at least two integer digits by using init(format:_:)
:
import Foundation
let string0 = String(format: "%02d", 0) // returns "00"
let string1 = String(format: "%02d", 1) // returns "01"
let string2 = String(format: "%02d", 10) // returns "10"
let string3 = String(format: "%02d", 100) // returns "100"
#2. Using String
's init(format:arguments:)
initializer
Foundation
provides Swift String
a init(format:arguments:)
initializer. init(format:arguments:)
has the following declaration:
init(format: String, arguments: [CVarArg])
Returns a
String
object initialized by using a given format string as a template into which the remaining argument values are substituted according to the user’s default locale.
The following Playground code shows how to create a String
formatted from Int
with at least two integer digits by using init(format:arguments:)
:
import Foundation
let string0 = String(format: "%02d", arguments: [0]) // returns "00"
let string1 = String(format: "%02d", arguments: [1]) // returns "01"
let string2 = String(format: "%02d", arguments: [10]) // returns "10"
let string3 = String(format: "%02d", arguments: [100]) // returns "100"
#3. Using NumberFormatter
Foundation provides NumberFormatter
. Apple states about it:
Instances of
NSNumberFormatter
format the textual representation of cells that containNSNumber
objects and convert textual representations of numeric values intoNSNumber
objects. The representation encompasses integers, floats, and doubles; floats and doubles can be formatted to a specified decimal position.
The following Playground code shows how to create a NumberFormatter
that returns String?
from a Int
with at least two integer digits:
import Foundation
let formatter = NumberFormatter()
formatter.minimumIntegerDigits = 2
let optionalString0 = formatter.string(from: 0) // returns Optional("00")
let optionalString1 = formatter.string(from: 1) // returns Optional("01")
let optionalString2 = formatter.string(from: 10) // returns Optional("10")
let optionalString3 = formatter.string(from: 100) // returns Optional("100")
Solution 3
For left padding add a string extension like this:
Swift 5.0 +
extension String {
func PadLeft( totalWidth: Int,byString:String) -> String {
let toPad = totalWidth - self.count
if toPad < 1 {
return self
}
return "".padding(toLength: toPad, withPad: byString, startingAt: 0) + self
}
}
Using this method:
for myInt in 1...3 {
print("\(myInt)".padLeft(totalWidth: 2, with: "0"))
}
Solution 4
Swift 3.0+
Left padding String
extension similar to padding(toLength:withPad:startingAt:)
in Foundation
extension String {
func leftPadding(toLength: Int, withPad: String = " ") -> String {
guard toLength > self.characters.count else { return self }
let padding = String(repeating: withPad, count: toLength - self.characters.count)
return padding + self
}
}
Usage:
let s = String(123)
s.leftPadding(toLength: 8, withPad: "0") // "00000123"
Solution 5
Using Swift 5’s fancy new extendible interpolation:
extension DefaultStringInterpolation {
mutating func appendInterpolation(pad value: Int, toWidth width: Int, using paddingCharacter: Character = "0") {
appendInterpolation(String(format: "%\(paddingCharacter)\(width)d", value))
}
}
let pieCount = 3
print("I ate \(pad: pieCount, toWidth: 3, using: "0") pies") // => `I ate 003 pies`
print("I ate \(pad: 1205, toWidth: 3, using: "0") pies") // => `I ate 1205 pies`
Jeehut
App- and Rails-Developer located in south-west Germany with love for great user interface design, smart software and compelling development tools and languages (like Swift and Kotlin).
Updated on February 06, 2022Comments
-
Jeehut over 2 years
I'd like to convert an
Int
in Swift to aString
with leading zeros. For example consider this code:for myInt in 1 ... 3 { print("\(myInt)") }
Currently the result of it is:
1 2 3
But I want it to be:
01 02 03
Is there a clean way of doing this within the Swift standard libraries?
-
Jeehut over 9 yearsAlthough this is not part of Swift it actually looks very clean. I think there just isn't a Swift native way of doing this so this might be the closest for now. Thank you, vacawama. :)
-
Jeehut over 9 yearsI think your answer is right when you want to format numbers the same way at multiple places. As I didn't ask for that I've chosen vacawama's answer as the correct but. But thank you for the answer! :)
-
Jeehut over 9 yearsBy the way: If I just wanted a single zero in front of my number I'd chose
println("0\(myInt)")
over your suggestion. That would use Swift native String class instead going through NSString formatting. -
Jose M Pan over 9 yearsIs useful until you get to "10", hehe
-
codecowboy almost 9 yearsHow about two leading zeros for anything between 0 > 100 ?
-
codecowboy almost 9 years@ImanouPetit. FYI, I used this with minimum number digits 3. If I don't explicitly unwrap i.e. let formattedNumber = formatter.stringFromNumber(counter)! then the strings contain Optional("001") so my code to dynamically choose an image path fails. Unwrapping with '!" solves the problem
-
vacawama almost 9 years
String(format: "%03d", myInt)
will give you"000", "001", ... , "099", "100"
. -
frank over 8 yearsWhy don't use this String(format: "%02d:%02d", arguments:[1,2]) ?
-
nhgrif almost 7 yearsThis may or may not work as the user expects if the
withPad
argument passed is more than a single character. -
possen about 6 yearsLike your repeatElement approach, see my answer for padding strings.
-
Codetard over 5 yearsThese's issue if value like
-3, -9
occurs, It still returns the same without a leading zero. -
vacawama over 5 years@SatnamSync, indeed negative numbers need extra care because you need to make space for the
-
sign. You can extend the field width by 1 for negative numbers, or useNumberFormatter
as described in part #3 of this answer. -
Codetard over 5 yearsYes, I implemented a negative integer check with if else statement. Your answer is very helpful. Thanks.
-
Mike Glukhov over 5 yearswhy?! what is the advantage of this?
-
cleverbit over 5 yearsThese will not work for two digit ints (eg. 10 becomes 010). Also the original question asked specifically for solutions involving Standard Libraries. The answer above by @ImanouPetit is preferred.
-
Nick N over 4 yearsextensions FTW..!! This also worked fine in Swift 4. For those of us struggling to move older code from 3, to 4, and eventually to Swift 5... :)