일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | |||
5 | 6 | 7 | 8 | 9 | 10 | 11 |
12 | 13 | 14 | 15 | 16 | 17 | 18 |
19 | 20 | 21 | 22 | 23 | 24 | 25 |
26 | 27 | 28 | 29 | 30 | 31 |
- c
- 앱 기획
- ipad
- 블러 효과
- BlurDrawable
- quintus
- nginx
- 공학인증
- StatefulWidget
- first_app
- first flutter app
- c++
- rotate circle
- Engineer Australia
- ABEEK
- game engine
- flutter
- flutter progress dialog
- PowerMockup
- 플러터
- 호주 이민
- HTML 게임 엔진
- StatelessWidget
- Android
- 기술인증
- OpenGL
- 회전판
- 맨붕
- reverse proxy
- progress
- Today
- Total
우동우동우's note
[iOS] Study Note 1 : iOS 입문, 간단한 객체 만들어보기 본문
기존에 사용하던 핸드폰의 지원금도 끊어지고 해서... iPhone5s를 질렀다. 기념으로 iPhone App 개발 공부를 좀 해보려고한다. 회사에서 선배들이 iOS 좀 공부해서 같이 하자고 몇 번을 얘기 했지만.. 그동안 프로젝트도 바쁘고 기기(Mac, iPhone)가 없어서 시도도 하지 못했다. ㅠㅠ 그러다가 이번에 마침 질러버렸다. 뭐 iOS 개발에 대한 공부를 해보려고 한다.
본인은 I Tunes U에 있는 Developing iOS 7 Apps for iPhone or iPad 강의를 들으면서 공부하면서 정리 차원에서 Study Note를 작성한다. 해당 강의는 10주 강의로 본 Note도 10개 정도 나오지 않을까? 생각된다. 그리고 내용을 추가를 할 때 언제든 할 예정이다. 뭐 강의를 직접 들으면 본 노트를 보는 것보다 훨씬 유익함을 미리 말씀드리면서 작성을 시작하도록 하겠다.
Object-C를 활용한 객체 만들어 보기
Object C는 기존의 C를 확장한 형태의 언어로 객체 지향적인 요소를 추가하였다. 그리고 그 형태가 조금씩 다르게된다. 그러다 보니 몇가지 기존의 프로그래밍과 다르게 생각을 해야하는 것들이 있다. 그중에 가장 두드러지는 것이 "Property"라는 것이다.
객체 내에 Property를 선언하게되면 getter와 setter를 포함하게 된다. 기존의 다른 객체 지향 프로그래밍에서는 getter와 setter를 별도로 선언해주어야 하지만 Object C 에서는 그렇지 않다. 예제를 보면 조금 더 상세하게 알 수 있다.
우선 프로젝트를 하나 만들어보자.
Empty 프로젝트 생성 한다.
SimpleObject라는 프로젝트를 하나 만들자.
새로운 그룹을 하나 추가
group의 이름을 src 라고 이름을 저장하고 New File을 눌러 파일을 만들자.
Object-C class 생성하자.
Card라고 이름을 지어보자.
자! 일차적인 준비는 여기서 끝이다. ㅎ
객체의 생성
그러면 Card.h와 Card.m 이렇게 2개의 파일이 생성될 것이다. Card.h파일은 기존에 우리가 익히 알고 있던 header 파일이다. (본인은 C와 C++가 익숙하지 않아 그렇게 익숙하지 않다. ㅠㅠ) header파일에서 기존의 C와 C++에서 하듯이 파라미터와 메소드 선언, super class 선언, framework(library) import 등에 대해 기술한다. 그리고 .m 파일에서는 .h파일에서 선언한 함수에 대해서 구체적으로 기술하면 된다. 보통 프로그래밍을 하는 사람들은 implement라는 말로 얘기를 하지만 한국말로 적용이라고 하기 좀 애매하긴하다... 뭐 아무튼 implement라고 하자. 앞으로도 그냥 이렇게 적어야 하겠다.
자. 이제 파일을 열어보자.
Card.h
#import <Foundation/Foundation.h> @interface Card : NSObject @end
Card.h
Card.m
#import "Card.h" @implementation Card @end
Card.m
Import
#import 라고 나와있는 부분이 보일 것이다. 이는 C에서는 #include에 해당하는 부분이고, Java는 동일하게 import를 의미한다. 즉, #import는 사용할 패키지 또는 파일에 대해서 선언해주는 것이다. Foundation/Foundation.h는 iOS의 전체 framework를 참조한다는 의미를 가져온다.
클래스 선언
.h 파일을 보면 @interface Card : NSObject가 나타나 있다. @interface <클래스 명> : <상위 클래스> 가 의미하는 것은 상위클래스에서 상속을 한다는 것을 의미한다. 여기서는 Card 클래스는 NSObject를 상속받는 다는 것을 나타낸다. 이는 .h파일에 작성해주어야한다. 그리고 @end라고 나타난 부분은 이 @interface를 마치는 곳을 나타낸다. 이 내부에는 필요한 Property, 함수 등을 선언하게 된다.
다음으로 .m 파일을 보면 @implementation Card, 그리고 @end라고 나타나있다. 이는 Card 객체를 implement 한다는 뜻이다. 여기서 각 함수별로 implement하게된다.
Property
property는 기존의 객체지향 프로그래밍에서 파라미터에서 getter와 setter를 포함한다고 생각하면 될 것이다. 아래의 코드를 보자.
Card.h
@interface Card : NSObject @property (strong, nonatomic) NSString *contents; @property (nonatomic, getter=isChosen) BOOL chosen; @property (nonatomic, getter=isMatched) BOOL matched; @end
여기서 보면 property로 선언한 contents, chosen, matched가 보일 것이다. 위의 코드는 property를 선언하는 방식이다. @property 지시자를 사용하여 선언을 하게된다.
여기서 strong이 의미하는 것은 해당 객체에 대한 모든 포인터가 nil로 선언이 될 때 메모리에서 지운다는 말이다. 그리고 strong과 대조적으로 week으로도 선언할 수 있다. 여기서는 해당 포인터를 소유하고 있는 객체가 nil이 되면 동시에 같이 메모리에서 해제된다는 의미를 가진다.
그리고 nonatomic은 여러 스레드에서 동시에 접근할 수 없다는 것을 표현하게된다.
이제 이 의미에 해대서 각가 코드로 보자.
Card.m
@implementation Card @synthesize contents = _contents; @synthesize chosen = _chosen; @synthesize matched = _matched; - (NSString *)contents { return _contents; } - (void)setContents:(NSString *)contents { _contents = contents; } - (BOOL)isChosen { return _chosen; } - (void)setChosen:(BOOL)chosen {  _chosen = chosen; } - (BOOL)isMatched { return _matched; } - (void)setMatched:(BOOL)matched { _matched = matched; } @end
실제로 위의 내용은 .m 파일에 적혀 있지만 의미는 위에 적혀 있는 것과 같다. 우선 content property를 보면 set* 형태와 같이 적혀있다. 그리고 property와 동일한 이름으로 함수가 만들어 진것을 볼 수 있다. property를 선언하면 해당 함수가 선언이 자동으로 된다. 하지만 .m파일에는 굳이 적을 필요가 없다. 만약 위에 적혀 있는 기능 외에 추가적인 기능이 필요한다면 Override하여 추가적인 코딩을 하면 된다.
그리고 chosen, matched를 보면 .h파일에 선언에 getter=is*와 같이 되어 있는 것이 보일 것이다. 이는 getter함수명을 새롭게 선언하는 방법이다. 이렇게 선언을 하게되면 .m에서 보는 것과 같이 getter 는 is* 형태로 변형되어 나타나게 되어 있다.
@synthesize 는 해당 property에 대해서 접근가능하도록 컴파일러에 선언하는 것을 의미한다. 이 또한 XCode에서는 자동으로 생성되게된다. 이를통해 property만 선언하게되면 해당 property에 접근하기 위한 접근자가 생성되게 된다는 것이다. 이는 _를 property를 앞에 붙이는 방식으로 자동으로 생성되게 되어 있다. 자신이 임으로 변경도 가능하다고 한다.
함수 선언
객체 지향이니 만큼 파라미터 외에 함수도 선언을 해보자.
Card.h
@interface Card : NSObject @property (strong, nonatomic) NSString *contents; @property (nonatomic, getter=isChosen) BOOL chosen; @property (nonatomic, getter=isMatched) BOOL matched; - (int)match:(Card *)card; @end
Card.m
@implementation Card - (int) match : (Card *) card { int score = 0; if ([card.contents isEqualToString:self.contents]) { score = 1; } return score; } @end
.h파일에 (<리턴타입>) <함수명> : (파라미터 타입) 파라미터명 ; 이런 형식으로 함수를 선언하게된다. 선언된 함수는 .m 파일에서 임플리멘트를 하게된다.
.m 파일에 대해서 조금 더 자세히 보게 되면 Object C에서는 함수를 부를 때 대괄호([])를 사용해서 나타내게 된다. 대괄호 형식은 다음과 같다.
[<객체> <함수명>:<파라미터>]
그래서 .m파일을 보면 contents는 NSString * 타입이라는 것을 알 수 있다. NSString 타입내에는 isEqualToString이라는 함수가 있는데 이 함수는 String을 비교하는 함수이다. 여기서는 card.contents가 객체를 나타내고 isEqualToString이 함수명, self.contents가 파라미터를 나타낸다.
그런데 이상한 점이 하나 있음을 알 수 있을 것이다. property를 선언하면 setter와 getter가 함수로 선언된다는 것을 위에서 말했는데 card.contents를 보면 대괄호([])를 사용하지 않은 것을 알 수 있다. 이는 property를 선언하면서 만들어지는 setter와 getter만 예외적으로 적용된다. 즉, setter와 getter는 점[.]으로 불러와도 무방하다는 점이다. setter와 getter를 대괄호 형태로 불러올 수 있다는 말이 된다.
오늘은 간단히 객체를 구현하는 정도를 공부했다. 강의에서는 MVC 패턴에 대한 고찰과 iOS Framework에 대한 설명이 있지만 본인이 iOS개발에 관한 MVC 패턴과 iOS 프레임워크 대해 기술하기에는 아직 부족한점이 많아(;;) 생략한다. 궁금하신 분들은 강의를 듣기를 바란다. 나중에 iOS에 대한 이해도가 높아지게 되면 기술 하는 것으로....