swift
swift - Options
행복하게사는게꿈
2021. 1. 6. 22:51
Options
swift는 총 9개의 Options를 제공함
메소드에서 Options 파라미터를 갖는 메소드에서 사용가능
Case Insensitive Option
대소문자 상관없이 비교
// swift에서는 모두 9개의 문자열 옵션을 제공
// String 문자열 메소드에서 opions 파라미터를 가진 메소드에서 모두 사용 가능
"A" == "a"
// .caseInsensitiveCompare() 메소드는 Bool을 리턴하는게 아니라 comparisonResult를 리턴하기 때문에
// .orderedSame같은 것으로 비교해 주어야 함
// 둘은 같은 코드
"A".caseInsensitiveCompare("a") == .orderedSame
"A".compare("a", options: [.caseInsensitive]) == .orderedSame
// compare 메소드의 options: [.caseInsensitive] 는
// NSString.CompareOptions.caseInsensitive를 생략한 것인데 왜 생략할 수 있냐면? 형식을 추론할 수 있기 때문에
Literal Option
리터럴 단위로 비교
// "한" 완성형
let a = "\u{D55C}"
// "한" 조합형
let b = "\u{1112}\u{1161}\u{11AB}"
// 최종문자가 같으면 true를 반환한다.
a == b
a.compare(b) == .orderedSame
// literal Options 사용 하면 false
// object-c랑 동일한 비교방법임 literal 단위로 비교
a.compare(b, options: [.literal]) == .orderedSame
Backwards Option
문자열의 검색 방향을 바꾸는 옵션
let korean = "행복하세요"
let english = "Be happy"
let arabic = "كن سعيدا"
// 문자열 시작부분이 왼쪽이 될 수도 있고 오른쪽이 될 수도 있기때문에
// swift는 문자열 시작부분이 Leading, 끝부분이 Trailing이라고 표현
// leading부터 검색
if let range = english.range(of: "p") {
english.distance(from: english.startIndex, to: range.lowerBound)
}
// trailing부터 검색
if let range = english.range(of: "p", options: [.backwards]) {
english.distance(from: english.startIndex, to: range.lowerBound)
}
Anchored Option
검색 대상을 제한
// backwords options과 혼동하기 쉬움
// backwords options은 검색 방향을 바꾸는거지 검색 대상을 바꾸는게 아님
// 전체 문자열을 대상으로 검색
// 이건 전체 문자열을 대상으로 하지 않음
// 검색 부분을 문자열 시작 부분이나 마지막부분으로 제한
let str = "Swift programming"
if let result = str.range(of: "Swift") {
print(str.distance(from: str.startIndex, to: result.lowerBound))
} else {
print("not found")
}
// backwords options
if let result = str.range(of: "Swift", options: [.backwards]) {
print(str.distance(from: str.startIndex, to: result.lowerBound))
} else {
print("not found")
}
if let result = str.range(of: "Swift", options: [.anchored]) {
print(str.distance(from: str.startIndex, to: result.lowerBound))
} else {
print("not found")
}
if let result = str.range(of: "Swift", options: [.anchored, .backwards]) {
print(str.distance(from: str.startIndex, to: result.lowerBound))
} else {
print("not found")
}
str.hasPrefix("swift")
if let _ = str.range(of: "swift", options: [.anchored, .caseInsensitive]) {
print("same prefix")
}
str.hasSuffix("swift")
Numberic Option
정확한 숫자 비교 옵션
// swift는 기본적으로 사전순으로 비교하지 않고 아스키 코드로 비교한다.
"A" < "B"
"a" < "B"
let file9 = "file9.txt"
let file10 = "file10.txt"
file9 < file10
file9.compare(file10) == .orderedAscending
// 9보다 10이 더 크지만 9랑 1이랑 비교되기 때문에 false
// 요롷게 해줘야 숫자끼리의 정상적인 비교가 된다.
file9.compare(file10, options: [.numeric]) == .orderedAscending
Diacritic Insensitive
발음 기호 무시하고 비교
// 발음기호 처리 option
// swift는 문자열 비교할때 우리 눈에 보이는 그대로를 비교
let a = "Cafe"
let b = "Cafè"
a == b
a.compare(b) == .orderedSame
// 발음기호 무시하고 문자 비교
a.compare(b, options: [.diacriticInsensitive]) == .orderedSame
Width Insensitive Option
반강문자 정강문자 비교?
// 아시아 국가에서 사용하는 문자들을 보면 정강문자와 반강문자로 표현할 수 있다.
// 반강문자는 정강문자의 절반의 넓이를 가짐
// 정강문자
let a = "\u{30A1}"
// 반강문자
let b = "\u{ff67}"
a == b // false
a.compare(b, options: [.widthInsensitive]) == .orderedSame // true
Forced Ordering Option
어떠한 경우에도 강제로 정렬
// 어떤 경우에도 강제로 정렬
let upper = "STRING"
let lower = "string"
upper == lower // false
upper.compare(lower, options: [.caseInsensitive]) == .orderedSame // true
// .forcedOrdering option은 전체옵션을 적용했을때 같은 문자열으로 판단된다면
// 일부 옵션을 무시하고 최대한 문자열의 순서를 파악할 수 있게 한다.
// 이 경우 caseInsenitive 옵션을 제외한다.
upper.compare(lower, options: [.caseInsensitive, .forcedOrdering]) == .orderedSame // false
Regular Expression
정규식으로 문자열 평가
// 주로 입력된 값을 검증할때 사용
let emailPattern = "([0-9a-zA-Z_-]+)@([0-9a-zA-Z_-]+)(\\.[0-9a-zA-Z_-]+){1,2}"
let emailAddress = "user@example.com😆"
// 이코드는 문자열 그대로를 비교하기 때문에 당연히 실패
if let _ = emailAddress.range(of: emailPattern) {
print("found")
} else {
print("not found")
}
// 파라미터를 정규식으로 처리한다.
if let range = emailAddress.range(of: emailPattern, options: [.regularExpression])
, (range.lowerBound, range.upperBound) == (emailAddress.startIndex, emailAddress.endIndex){
print("found")
} else {
print("not found")
}