아리의 iOS 탐구생활

[Swift] 시간과 날짜를 다루는 타입에 대해서 알아보자. 본문

Swift/iOS

[Swift] 시간과 날짜를 다루는 타입에 대해서 알아보자.

Ari Lee 2021. 8. 25. 14:34
반응형

Date 관련 타입들은 앱 개발을 할때 굉장히 많이 사용하게 되는 타입중 하나이다.
시간과 날짜를 다루는 타입들은 swift 기본 프레임워크인 Foundation에 포함되어 있다.

 

 

🔍  Date

 

Apple Developer Documentation

 

developer.apple.com

Foundation의 Date 타입은 전 세계적으로 정확히 같은 시간을 표현하기 위한 타입이다.

 

  • init()
    현재 시간을 나타내준다.

 

  • init(timeIntervalSinceNow: TimeInterval)
    현재 시각으로 부터 입력한 초 이후의 시점을 나타낸다.

 

  • init(timeInterval: TimeInterval, since: Date)
    다른 Date()객체로부터 입력한 초 이후의 시점을 나타낸다.

 

  • init(timeIntervalSince1970: TimeInterval)
    1970년 1월 1일 00:00:00 UTC를 기준으로 주어진 초 단위로 초기화된 'Date'를 리턴한다.

 

  • init(timeIntervalSinceReferenceDate: TimeInterval)
    2001년 1월 1일 00:00:00 UTC를 기준으로 지정된 초 단위로 초기화된 날짜 값을 생성합니다.

 

👉🏻  example

// 1. 현재 시간
let date1 = Date()
// 2. 지금으로부터 300초 지난 시점
let date2 = Date(timeIntervalSinceNow: 300)
// 3. date2로부터 300초 지난 시점
let date3 = Date(timeInterval: 300, since: date2)
// 4. 유닉스 시간인 1970년 1월 1일 00:00:00 UTC로부터 300초 지난 시점
let date4 = Date(timeIntervalSince1970: 300)
// 5. 2001년 1월 1일 00:00:00 UTC로부터 300초 지난 시점
let date5 = Date(timeIntervalSinceReferenceDate: 300)

print(date1) // 2021-08-24 11:49:10 +0000
print(date2) // 2021-08-24 11:54:10 +0000
print(date3) // 2021-08-24 11:59:10 +0000
print(date4) // 1970-01-01 00:05:00 +0000
print(date5) // 2001-01-01 00:05:00 +0000
  • Date를 이용하여 특정 코드의 연산 실행시간도 측정할 수가 있다.
// Date를 이용하여 특정 코드의 연산 실행시간을 측정할 수 있다.
let currentDate = Date()
print("실행 시간 : \(-currentDate.timeIntervalSinceNow)")
// print가 되기 전까지의 실행시간을 나타낸다.

 

 

 

 

🔍  TimeInterval

 

Apple Developer Documentation

 

developer.apple.com

TimeInterval 타입은 날짜 및 시간 관련한 표현에 사용하는 타입으로 초(second)를 나타낸다. 즉, 값이 1이면 1초를 나타낸다. 그러나 사실 TimeInterval은 이름만 다른 Double 타입이다. 타입 별칭(Type alias)이라는 기능을 활용하여 이름만 달라진 것이다. 이미 존재하는 타입의 기능을 똑같이 구현할 필요는 없으나 Double이라는 이름보다는 TimeInterval이라는 이름으로 표현하는 것이 더 직관적이므로 타입 별칭을 사용해준 것이다.

 

 

 

 

🔍  DateFormmatter

 

Apple Developer Documentation

 

developer.apple.com

시각(Date)과 문자열 표현(String)을 상호 변환해주는 역할을 수행하는 타입이다. 시간을 원하는 타입으로 만들 수 있다. Date타입은 날짜의 한 지점을 나타내지만 이것을 텍스트로 표현하고 싶을 때에 주로 활용한다. DateFormatter을 인스턴스화 시켜 사용하며 dateStyle, timeStyle, locale, 그리고 dateFormat을 통해 다양한 방법으로 Date를 표시한다. 

 

👉🏻  example

let date = Date()
let dateFormatter = DateFormatter() // 인스턴스 생성
dateFormatter.dateStyle = .medium
dateFormatter.timeStyle = .medium

dateFormatter.locale = Locale(identifier: "en_US")
print(dateFormatter.string(from: date)) // Aug 24, 2021 at 8:55:52 PM

dateFormatter.locale = Locale(identifier: "fr_FR")
print(dateFormatter.string(from: date)) // 24 août 2021 à 20:55:52

dateFormatter.locale = Locale(identifier: "ko_KR")
print(dateFormatter.string(from: date)) // 2021. 8. 24. 오후 8:55:52

dateFormatter.dateFormat = "YY년 M월 d일 h시 mm분 ss초"
print(dateFormatter.string(from: date)) // 21년 8월 24일 8시 55분 52초

DateFormatter 사용하면 String으로부터 Date 얻어오는 것도 가능해진다. String DateFormatter 형식과 맞지 않을 경우에는 nil 리턴해야 하므로 반환형이 Optional이다.

 

// 인스턴스 생성
let formatter = DateFormatter()

// Date to String
let now = Date()
let formatter = DateFormatter()
formatter.dateFormat = "yyyy년 MM월 dd일 HH시 mm분 ss초"
let result = formatter.string(from: now)
print(result) // 2021년 08월 24일 20시 08분 32초


// String to Date
let dateString = "2021년08월24일 20시10분11초 +0000"
formatter.dateFormat = "yyyy년MM월dd일 HH시mm분ss초 ZZZZ"
let date = formatter.date(from: dateString)!
print(date) // 2021-08-24 20:10:11 +0000

변환하는 결과가 옵셔널인 이유는 변환할 문자열이 포맷이랑 동일하지 않을 수도 있기 때문이다. 위 예제에서는 강제 언래핑을 사용하고 있지만 에러가 발생할 수 있으므로 옵셔널 바인딩을 해야한다.

 

👉🏻  포맷 용어 정리

Format Desctiption Example
y (년도) 연도 출력 2021
yy 연도 뒷자리 두개 출력 21
yyyy 연도 네자리 출력 M 월 출력 2021
M (월) 월에서 뒷자리 하나 (ex: 2) 8
MM 월을 두자리로 (ex: 02) 08
MMM 영문 약어로 (ex: feb, sept) Aug
MMMM 영문으로 (ex: february, september)
d 날짜 출력 h, H 시간 출력
August
d (일) 일 출력 25
dd 일을 두자리로 출력 25
E, EE, EEE (요일) 요일을 약어로 출력 (Locale에 따라 다름) Wed
EEEE 요일을 전체적으로 출력 Wednesday
EEEEE 요일을 한글자로 출력 W
EEEEEE 요일을 두글자로 출력 We
a (오전, 오후) 오전, 오후를 출력 (Locale에 따라 다름) PM or AM
h (시간) 시간을 12시간으로 한자리로 출력 2
hh 시간을 12시간으로 두자리로 출력 02
H 시간을 24시간으로 한자리로 출력 14
HH 시간을 24시간으로 두자리로 출력 14
m (분) 분을 한자리로 출력 5
mm 분을 두자리로 출력 05
s (초) 초를 한자리로 출력 1
ss 초를 두자리로 출력 11
S (밀리초) 밀리초를 한자리로 출력 0
SS 밀리초를 두자리로 출력 12
SSS 밀리초를 세자리로 출력 123
zzz (시간대) 타임존을 3글자로 출력한다. 이름을 모르는 경우 GMT-08:00으로 대체 GMT+9
zzzz 타임존의 이름을 상세하게 출력한다. Korean Standard Time
ZZZZ 타임존의 약어와 hour offset를 출력 GMT+09:00
Z RFC 822 GMT 포맷 방식 출력 +0900
ZZZZZ ISO 8601 타임존 포맷 방식 출력 +09:00

 

 

 

 

🔍  TimeZone

 

Apple Developer Documentation

 

developer.apple.com

말 그대로 타임존의 명칭을 의미한다. 세계의 각 지역에 따라 시간대가 다른데, 그 시간대를 나타내기 위한 Foundation의 타입이다. 날짜 계산이나 날짜 표현 등의 작업을 수행할 때 꼭 TimeZone을 잘 확인해야 한다. 같은 시각이라도 TimeZone에 따라서 날짜 표현이 달라질 수 있기 때문이다.

 

👉🏻  example

let date = Date()
let formatter = DateFormatter()
formatter.dateFormat = "yyyy-MM-dd HH:mm:ss"
formatter.locale = Locale(identifier: "ko_kr") // 한국의 시간을 지정해준다.
formatter.timeZone = TimeZone(abbreviation: "KST") // 한국의 시간대로 지정한다.
//formatter.timeZone = TimeZone.current // 현재 사용자의 시간대를 지정한다.

let kr = formatter.string(from: date) // Date to String
print(kr) // 2021-08-25 01:17:53

 

 

 

 

 

🔍  Calendar

 

Apple Developer Documentation

 

developer.apple.com

달력과 관련된 정보를 담는 구조체이다. 달력과 관련된 계산과 각 달력의 요소인 DateComponent를 얻을 수 있다.

Calendar의 생성은 Calendar.Identifier 열거형을 init 메소드에 전달함으로써 이루어지는데 이는 나라 또는 종교 별로 달력이 다르기 때문이다. 인스턴스로 만든 뒤에는 달력의 요소를 나타내는 DateComponent 구조체에 관한 다양한 메서드를 사용할 수 있다. Date에서 DateComponent를 뽑아낼 수도 있고 반대로 DateComponent를 통해 Date를 만들어 낼 수도 있다.

 

👉🏻  example

let date = Date()
var calendar = Calendar(identifier: .gregorian)
print(calendar.dateComponents([.day, .month], from: date)) // month: 8 day: 25 isLeapMonth: false

var dateComponents = DateComponents()
dateComponents.year = 1995
print(calendar.date(from: dateComponents)) // Optional(1994-12-31 15:00:00 +0000)

 

그 외에도 AM/PM, WeekDay, Month, Quarter, Era 등 locale 설정 별로 달라질 수 있는 Symbols의 배열을 얻을 수도 있다.

// Calendar로부터 날짜 요소별 Symbol 얻기
var calendar = Calendar(identifier: .gregorian)
calendar.locale = Locale(identifier: "ko_kr")
print(calendar.amSymbol, calendar.pmSymbol) // 오전 오후
print(calendar.eraSymbols) // ["BC", "AD"]
print(calendar.weekdaySymbols) // ["일요일", "월요일", "화요일", "수요일", "목요일", "금요일", "토요일"]
print(calendar.quarterSymbols) // ["제 1/4분기", "제 2/4분기", "제 3/4분기", "제 4/4분기"]
print(calendar.monthSymbols) // ["1월", "2월", "3월", "4월", "5월", "6월", "7월", "8월", "9월", "10월", "11월", "12월"]
print(calendar.longEraSymbols) // ["기원전", "서기"]

 

 

 

 

🔍  DateComponents

 

Apple Developer Documentation

 

developer.apple.com

자료형을 살펴보면 Optional타입이다. 그래서 모든 파라미터를 전달하지 않더라도 기본값이 nil이기 때문에 원하는 파라미터만 골라서 사용할 수 있다.

 

👉🏻  example

아래는 DateComponents를 활용하여 원하는 년,월,일만 생성하여 원하는 포맷으로 설정하는 과정이다.

var calendar = Calendar(identifier: .gregorian) // 인스턴스 생성: 캘린더 유형 설정
let dateComponents = DateComponents(year: 2222, month: 2, day: 22) // 원하는 요소만 입력하여 날짜 추출
let myDate = calendar.date(from: dateComponents) // date타입으로 변환. 옵셔널 타입이다.

let formatter = DateFormatter() // 포맷설정을 위해 인스턴스 생성
formatter.locale = Locale(identifier: "ko_kr") // 한국 시간으로 지정
formatter.dateStyle = .full // 날짜스타일 지정
print(formatter.string(from: myDate!)) // 2222년 2월 22일 금요일

 

아래와 같이 날짜의 각 요소들을 추출할 수도 있다.

let date = Date()
print(calendar.dateComponents([.weekday, .day, .month, .year], from: date)) // year: 2021 month: 8 day: 25 weekday: 4 isLeapMonth: false

 

 

 

 

 

 

 

 

Reference

 

날짜 다루기

iOS에서 날짜를 다루는 방법에 대해 알아보자.

medium.com

 

NSDateFormatter.com - Easy Skeezy Date Formatting for Swift and Objective-C

NSDateFormatter.com Easy Skeezy Date Formatting for Swift and Objective-C ... Wednesday, Aug 25, 2021 EEEE, MMM d, yyyy 08/25/2021 MM/dd/yyyy 08-25-2021 05:07 MM-dd-yyyy HH:mm Aug 25, 5:07 AM MMM d, h:mm a August 2021 MMMM yyyy Aug 25, 2021 MMM d, yyyy Wed

nsdateformatter.com

 

[Date] Swift에서 Date를 이용하는 여러 케이스들 모음

Date 연산을 구현할때, 까먹어서 구글링해서 찾아보고 구현하고... 이렇게 했는데 이제 이렇게 안하려고 SPM에 넣었습니다 :-) 제가 필요해서 구현했던 것을 공유합니다 :-) [1] 특정 Date에서 정보를

eunjin3786.tistory.com

 

Date Formatters

Date Formatters There are two basic methods you use to create a string representation of a date and to parse a string to get a date object using a date formatter—dateFromString: and stringFromDate: respectively. You can also use getObjectValue:forString:

developer.apple.com

 

반응형
Comments