Saturday, April 2, 2011

iphone 개발 수업 4주차-2

4/2
<frame work>
frameworks 는 라이브러리다. 프레임 워크를 사용하려면 이를 프로젝트에 add 해야 한다(라이브라러파일을 같은 폴더에 넣어야 한다).


<UITable View 다시 보기>
UITableViewDataSource; 내용관리, 관련 메소드는 교재 159p
UITableViewDelegate; 이벤트 관리(셀선택, 셀 내용편집 및 삭제), 관련 메소드는 교재 167p


UIApplication 객체가 이벤트를 감시하고 있는데 화면의 셀을 선택하면 UIApplication 객체가 UITableViewDelegate 객체의 didSelectRowAtIndexPath 메소드를 호출한다. 이때 넘겨주는 인자가 NSIndexPath 객체, 이 객체는 속성으로 section(선택된 센션 인덱스)와 row(선택줄의 인덱스)를 가지고 있다.


프로토콜은 자바의 인터페이스와 동일, 속성은 없고 구현을 하지 않은 메소드만 존재, 대표적으로 UItableDelegate와 DataSource.




<ViewController 하나 더 만들기>
navigation based application 을 만들면 하나의 ViewController 만 생기는데 하나의 화면을 더 만들고 싶으면 classes에서 우클릭해서 add , new File, 거기서 UIViewController subclass를 선택(UIViewController 클래스를 상속받는 클래스). 옵션도 선택(iPad용이냐, UITableViewController 를 상속 받을 것이냐, xib 즉 xml 파일을 만들 것이냐).
그리고 UInavigation Bar 에 right 버튼을 생성하거나 back 버튼 대신 다른걸 만들고 싶을 때 Bar Button Item 클래스(버튼 클래스와 비슷한데 다만 단순화 시킨것, 곧 클릭했을때의 이벤트만 메소드로 가지고 있음)를 가져오는데 interface builder에다가 navigation bar 위치에 넣을려면 안되고 xib 에다가 넣는다. 이것들을 UIViewController의 UIBarButtonItem 클래스의 변수에 연결시키고 또 이것이 선택되어졌을 때(이벤트가 발생했을때) 진행되어야 할 메소드를 연결시킨다.


UIViewController 의 initWithNibName 메소드(이때 인자가 xib 파일의 이름과 그 파일의 경로(bundle의 인자, nil이면 현재 경로))를 사용하면 xib 파일과 객체를 연결시켜준다.  




<셀의 UI 바꾸기>
xib 를 하나 생성하는데 user interface 에서 View xib를 선택. 그러면 View 에 관한 interface가 생기는데 이걸 생성하려는게 아니기 때문에 이 View 를 지운다음에 Table View Cell 을 라이브러리에서 xib로 가져온다. 그런다음에 그 UI, 즉 Table View Cell에 넣을 UI 를 라이브러리에서 가져다가 Table View Cell 안에 드레그 한다. 그리고 이것들(Table View Cell 안의 다른 UI들, 즉 UIImage나 UILabel들)의 객체를 리턴 받아야 하는데 이때 사용하는 것이 tag. 그 다음에 이 변형된 table View cell을 갖을 delegate(여기서는 RootViewController)로 가서 cellForRowAtIndexPath메소드를 바꿔준다. NSArray * topLevelObjects = [[NSBundle mainBundle] loadNibNamed:@"PhotoTableCell" owner:self options:nil] ; 이렇게 하면 topLevelObjects에는 DOM(Document Object Model) 형식의 객체가 리턴된다. 이 DOM에는 PhotoTableCell.xib의 객체들이 트리 형태로 들어 있게 된다. 이 DOM 객체를 가르키는 topLevelObjects는 index로 DOM 안의 객체(Table View Cell, UIImage, UILabel)로 접근하거나 아니면 앞에서의 tag로 접근 가능하다.


결론은 특정 UI를 바꿀려면 UI 안에 UI를 넣은 xib 파일(그러니까 변형된 UI)을 만들고 NSBundle mainBundle로 가져온다.
---------------------------------------------------------------------------------------------


<메모리 관리>
저장 장치, 그러니까 하드디스크에 저장된 것은 클래스, 이것을 메모리에 올리면 객체가 된다(메모리에 올려야 작동). 메모리에 올리려면 사용하는 메서드가 alloc 제거하려면 사용하는 메서드가 dealloc 이는 둘다 NSObejct클래스가 가지고 있는 메소들이다. 그런데 dealloc은 잘 사용하지 않음(다른 변수가 참조 할때 dealloc 해서 메모리에서 지우면 다른 변수가 참조시 에러가 나기 때문). 그래서 이때 사용하는 것이 NSObject의 retainCount라는 속성. retainCount는 몇개의 포인터에서 이 객체를 참조하는가 하는 카운트 값을 가지고 있다. 초기값, 그러니까 처음 생성되면 1을 갖는다. 이 retainCount 값은 NSArray, NSSet, NSDictionary, UITableView등에 삽입시 1 증가.  또 retain 메소드 호출시 1 증가. 반대로 NSArray등에서 빼거나 release 메소드를 호출하면 1 감소. retainCount가 0이 되면 자동으로 그 객체는 자동으로 삭제된다.


A *a = [[A alloc] init]; 이렇게 하면 반드시 release를 해야 한다.
A *a = [[[A alloc]init] autorelease]; 구현된 메서드 init()이 끝나면 자동으로 [a release]를 호출.


autorelease는 문제점이 하나 있는데 특정 메소드에서 객체를 생성해서 그 객체를 return 할때 autorelease를 하면 객체를 리턴받을때 삭제되어 있는 상태기 때문에 에러가 난다. 그래서 이럴때 autorelease를 사용하면 반드시 retain 메소드를 호출해야 한다. 


즉 상황에 따라 autorelease 를 사용하는 것이 좋을때도 있고 나쁠 때도 있는데 한 메소드 안에서 잠시 사용하는 것은 autorelease를 사용하는 것이 좋다.


autorelease모드인 경우 : 1.객체 생성이 autorelease 명시시, 2. alloc을 안해준 객체 생성, 예를 들어 [NSDictionary initWithArray:array]
-------------------------------------------------------------------------------------------------


<데이터 저장>
1.파일에 저장: NSFileManager사용
2.메모리의 저장 : 어플 종료시 내용 사라짐
3.코어 데이터 : sqlite 사용. 저장, 로드, 검색이 가능. ORM(객체 지향 DB); 직접 query를 이용하는것이 아니라 객체를 통해서 query를 던지다.


NSPersistentStoreCoordinator ; 파일(바이너리)을 읽어서 내용을 꺼내줌, 즉 파일에 있는 정보를  NSPersistentStoreCoordinator에 query를 던지면 관련 entity를 NSManagedObjectContext에 NSManagedObject 객체 형태로 메모리에 올린다. 이때 query를 던지는 클래스는 NSFetchRequest. 

Friday, April 1, 2011

iphone 개발 수업 4주차

4/1
<UI table view>
보통 서버에서 UI table view 의 리스트를 10~20 정도씩 받아온다(한꺼번에 다 받아 오는게 아니라).  그리고 아이폰은 터치해서 리스트 스크롤을 올리면 윗 셀이 없어지고 아래 셀이 생기는데, 이것은 없어지는 셀이 재사용 큐에 들어갔다가 내용이 바뀌어서 다시 UI table view 에 보이는 것이다. 그런데 table view에 여러개의 섹션이 있을때 각 섹션에서 없어지는 셀이 재사용큐에 들어갔다가 다시 재사용되는데 이때 어떻게 셀들을 구분하느냐, 식별자를 이용해서 이를 구별한다.
--------------------------------------------------------------------------------------------------


<Navigation 기반 application의 구조(World photos 예) > 
WorldPhotosAppDelegate ; 시스템 이벤트를 처리
   UINavigationController *navigationController; 화면 전환하는 객체(화면을 구성(backButton(혹은 leftButton), text, rightButton(이를 UINavigationBar라 함) 과 View가 있다), stack을 가지고 있어서 그 안에 UIviewController들이 있다. 이중에 하나를 선택헤서 View에 나타냄)


RootViewController ; RootViewController 객체가 생기면 RootViewController.xib xml에 안에 있는 내용을 나타냄(이벤트도 관리) , 이것이 첫 화면인데 이는 navigationController 의 stack에 첫화면으로 저장되어 있어서 이를 view 에 나타내기 때문이다.


RootViewController 의 UINavigationItem ; UINavigation Bar의 내용 설정, RootViewController가 이를 속성으로 가지고 있다.


PhotoDetailViewController ; photoDetailViewController.xib 이름의 xml 파일(이것은 interface builder로 만듬)의 객체를 생성하고 그 화면의 이벤트를 처리.


PhotoDetailViewController 의 UINavigationItem ; UINavigation Bar의 내용 설정


%%WorldPhotosAppDelegate와 navigationController는 RootViewController와 PhotoDetailViewController 에 의해 공유된다.%%
%%[[UIApplication sharedApplication]delegate]; 하면 UIApplication에서 공유하고 있는 것중 delegate를 return, 그러니까 WorldPhotosAppDelegate 를  return.%%


처음 시작하면 navigationController stack에는 RootViewController만이 들어 있다. 그래서 그것이 화면에 보이게 됨. RootViewController의 didSelectRowAtIndexPath 메소드 안에서 [self.navigationController pushViewController:detailViewController animated:YES]; 처럼 공유하고 있는 navigationController의 pushViewController메소드를 이용해서 화면에 보이고자하는 viewController, 즉 여기서는 detailViewController를 stack에 넣어서 화면 전환이 일어나게 한다(animated 는 화면을 자연스럽게 바꿀것인지, 아니면 확 바꿀 것이지를 나타냄). 이렇게 해서 detailViewController가 화면에 나타나게 되는데 이때는 UInavigation Bar 에는 backButton이 생기는데(RootViewController 화면에서는 이 버튼이 없다, 첫화면이라) 이 버튼을 누르면 다시 뒤 화면, 즉 RootViewController의 화면이 나타나게 되는데 이는  [self.navigationController [popViewController]]; 를 실행해서 stack 안에 detailViewController를 제거했기때문이다.

EstimateS and something others

두가지에 막혀 있다. 어쩌면 세가지. 하나는 taxonomic rank에 대한 이해가 부족하다. rank term. 어떤건 kingdom, phylum, class, order등의 정보가 다 있는데, 어떤건 그러하지 않고, 그러하지 않는건지 아니면 내가 그 tern을 제대로 특정 rank에 놓지 못한것이지도 판단이 되지 않는다. 다른 하나는 통계학적 접근. 다른 하나는 aligner에 대한 것. 어찌보면 핵심부에 속하는 것들에 지금 막혀있다. 힘빠져.
하나씩 해야지. 이번에 통계적인 것에 대한 내용을 들여다 보려 한다. 시작은 EstimatS라는 프로그램의 설명부터 해서 species richness, 그리고 두 community 간에 shared species를 계산하는 논문까지(항상 그렇듯 계획은 좋다. 시작은 창대하나 끝이 미약해서..).

<EstimateS>
http://viceroy.eeb.uconn.edu/EstimateSPages/AboutEstimateS.htm
일단 뭔지는 모르나 EstimateS가 하는 일부터 알아보자. 


-rarefaction and species accumulation curves
일단은 expected spcies accumulation curves(=sample-based rarefaction curve)를 구한단다. 이건 resampling technique이 아니라네. 그리고 individual-based rarefaction curves를 구한다.


-species richness estimators and diversity indices
non-parametric species richness를 구한다. 그런데 sample-based data와 abundance-based data에 대해서. 음.. log-linear confidence interval을 구한다. sample-based rarefaction curve의 aymptotic function에 기초한 species richness estimator를 구한다.


-shared species estimation and biotic similarity indices, with estimators
sample pairs에 대해 Chao's estimator of total shared species를 구한다.




아.. 전혀 알아들을수 없다. 좀더 자세한 user guide를 봐보자.
http://viceroy.eeb.uconn.edu/EstimateSPages/EstSUsersGuide/EstimateSUsersGuide.htm

-Introduction
일단 용어 정리부터 한다. 
sample 이라 함은 특정 지역, 면적, 내지는 시간 단위의 list of species 또는 OTU를 의미. 
species abundance data(=abundance data)는 counts로 sample 안에 각 species의 counts, 즉 수를 의미.
incidence data라 함은 presence/absence(=occurrence) data 으로 sample 안에 각 species가 있냐 없냐를 의미하는 데이터. 
마지막 말은 좀 이해 안되네. abundance data랑 summed incidence data랑 같은거 아닌가. summed incidence data가 frequencies of occurence 라면 어짜피 count인데.. 요건 음 패스. 여튼 이로써 뭐에 대해 뭘 구한다라는 말에서 뭐에 대해가 좀 이해가 되는듯.
아 이 뒤의 내용은 아무래도 Gotelli & Colwell (2001) 를 봐야 할거 같아서 급선회 한다.


<Quantifying biodiversity: procedures and pigfalls in the measurement and comparison of species richness>
-Taxon sampling curves
species richness가 중요한 measurement이긴 한데 정확히 측정하기 어렵다. 왜? 다양한 taxa가 있는 곳에서는 sampling을 많이 할수록 species가 많은걸로 나올테니까.
근데 speices 
taxon sampling curve를 4가지로 분류. 기준은 1. sampling protocol(individual-based 냐 sample based냐), 과 2. accumulation curves냐 rarefaction curves냐 .
첫번째 기준의 individual based라 함은 그냥 두특정 locality의 species를 비교할때 individual based 방식은 특정 locality에서 랜덤하게 sampling해서 species를 카운트 하는것이고 sample based는 특정 locality를 quadrat으로 구획해서 나눠진 quadrat중 계산되어진  quadrat의 species를 축적해서 더하는것. 
두번째 기준의 accumulation curve는 말그대로 데이터 collection과정중에 생기는 species 값을 축적해서 curve를 그리는것. 반면 rarefaction curve는 1부터 N 까지 random sampling을 반복적으로 해서 나오는 average species count를 그린것.
accumulation curve는 왼쪽에서 오른쪽으로, 반면에 rarefaction curve 오른쪽에서 왼쪽으로 그려지는데. 이는 rarefaction curve가 accumulation curve의 right end를 기준으로 sampling 사이즈를 변화하면서 반복적으로 sampling해서 나온 average species count를 기록하기 때문. 
그리고 sample-based curve가 individual-based curve보다 아래 있는데 이는 spatial or temporal autocorrelation 에 의한것.


-Comparing assemblages using taxon sampling curves
두 communities가 측정된 species richness가 다를수 있는데, 이는 진짜 생물학적으로다가 다를 수도 있는것이고 아니면 sampling effort나 condition의 차이에 의한 것일수도 있다. 그렇기에 그냥 raw taxon count를 비교하는건 문제가 있다.
만약 accumulation curves가 asymptote에 닿으면 raw count를 비교하는게 의미 있을수도 있으나 거의 그럴 일은 없다. 그러나 appropriate scaling을 통해서 accumulation curve를 비교하는게 가능. individual-based dataset의 경우 현실적인 문제(individual을 조사할때 보통 순서 까지 recording 하지 않기 때문)에서 accumulation curve를 구하는것이 문제가 있는데 이럴땐 rarefaction 을 이용.   individual의 경우 individual-based rarefraction만 사용 가능.하지만 sample-bassed 데이터의 경우 individual-based, sample-based rarefraction을 둘다 사용가능. 근데 sample-based을 사용(patchiness 때문에 individual-based rarefaction은 overestimate된다). sample-based rarefaction curve를 사용한다고 하더라도 taxa의 수를 plot 할 때는 individual의 accumulate의 수로 해야 한다(sample당 individual의 갯수가 다르므로).




-Computing rarefaction curves
1.individual-based rarefaction
randomize를 위한 re-sampling 말고 combinatoric theory에 근거한 mathematical expression이 있다. Sanders이야기 하는데 여튼 이건 틀린거고 hypergeometric sampling distribution에 근거한 derivation model이 있다. 그리고 Coleman의 random placement curve를 이용하면 빠른 계산이 가능하다
2.sample-based rarefaction


-Category-subcategory ratios and their pitfalls
1.individuals and species
2.species and genera


-Species richness VS. species density


-Asymptotic estimators of species richness

http://www.vsni.co.uk/products/genstat/htmlhelp/ecology/AccumulationCurve.htm
그럼 species accumulation curve는 어따 쓰냐? species richness를 추정하는데 사용한다. asymptotic line이 species richness가 되는건가.. 
그리고 rarefaction이라 함은 sampling effect가 특정 level까지 떨어질때의 species의 갯수를 추정하는데 사용하는 method.

Monday, March 28, 2011

binary 데이터 핸들링

요즘 binary 데이터를 처리할 일이 많이 생긴다. sff 파일도 그렇고 ab1파일도 그렇고. 단 한번도  binary 파일을 처리해보지 못한 나에겐 공포의 영역. 해서 함 해보기로 한다. 까짓거 사람이 만든건데 뭐 별거 있겠어.


우선은 누가 짜놓은 ab1 파일 파싱하는 프로그램을 봤는데 struct 모듈을 사용한다.

http://www.thegreatgoodplace.com/tt/study/316 (길원이형 블로그를 보게 될 줄이야...)


헌데 잘 이해가 안된다. 우선 쉬운 블로그를 찾아보자.

http://seorenn.blogspot.com/2011/02/python-struct-padding.html


음.. 때려 맞추자면 pack이 binary로 만들어 주는거고 unpack이 binary로 된걸 python 형식의 string으로 바꿔주는듯.. padding이란 말이 나오는데 뭐 % operator에 숫자 붙인 것처럼 데이터가 특정 사이즈만큼 안될 때 0 bit로 넣어주는거 같고.. 음.. 생각해보니 binary 라는게 그냥 데이터가 틈(?) 없이 계속 나열되어 있는 것이겠군. 그렇다면 파일 format 그러니까 몇바이트까지가 하나의 데이터고 또 몇바이트까지가 하나의 데이터고 이런 정해진 포멧만 알고 특정 바이트까지로 구분해서 읽으면 그게 데이터가 되겠다는 생각이 든다. 아닐수 있지만.. 여튼


이제 struct 모듈의 full 설명을 볼 차례다.
http://docs.python.org/library/struct.html
pack이랑 unpack은 위에서 말한거랑 같고 pack_into랑 unpack_from 이 있는데 이는 특정 buffer에서 offset 값서 부터 읽거나 쓰는거 같은거..  
byte order, size, and alignment 아.. 요것이 중요한거 같은데. format 의 첫 character가 @,=,<,>,!(!는 poor souls을 위한 거란다. 나인가 보다 네트워크는 big인걸 까먹는 나) 중에 하나 선택하는건데 이게 byte order, size, alignment를 뭘로 할거냐. 그러니까 native 라 함은 하드웨어 특유의 방식 byte order 같은 경우에는 intel cpu의 경우 little endian 이다 뭐 이런거 뜻하는 걸거고(확인하려면 sys.byteorder를 사용하란다).. size는 링크 안에 표가 있다. 아.. 근데 alignment가 뭔지 모르겠다.. 뭐지 이거.. 아. 예제를 보아하니 format이 다른 연속의 데이터가 있을때 이를 맞춰주는거를 alignment라고 하는거 같은데 정확하지 않다.




첫 url 링크의 프로그램을 보면 ab1 파일의 binary format과 프로그램이 있는데 struct를 알고보면 굉장히 프로그램이 단순다하는 걸 알게 된다. 다만 전부 unpack의 format이 big-endian 인데 이는 ab1 파일 자체가 그렇게 되어 있기 때문에.


아 그리고 전에 포스팅 했던 bit 연산자도 다시 볼 필요가 있겠다.
http://graphy21.blogspot.com/2010/10/bit.html

Saturday, March 26, 2011

iphone 개발 수업 3주차-2

3/26
<UITable view>
같은 형태의 데이터를 list 형태로 반복해서 출력. MVC로 구성
섹션: 리스트에서 그룹
섹션 헤더 : 섹션의 이름
섹션 푸터 : 섹션 마지막의 메뉴같은것(?)
셀 : 그룹을 이루는 하나 하나의 항목; contentView


UITableView : MVC 에서 view의 역할


UITableViewDataSource : MVC 에서 model의 역할, 데이터 관리
-(NSInteger)numberOfSectionInTableView:(UITableView *)TableView ; 섹션(group)의 수를 return(섹션이 없을때 return 값은 1)
-(NSInteger)tableView:(UITableView *)TableView numberOfRowsInSection:(NSInteger*)section;
-(UITableViewCell *)tableView:(UITableView *)TableView cellForRowAtIndexPath:(NSIndexPath*)indexPath
UITableViewDataSource 에서는 위의 3 메소드를 반드시 정의해줘야 한다.


UITableViewDelegate : controller의 역할, 이벤트 관리


MainWindow 객체 안에 UITableView가 있고 MainWindow화면을 관리하는 UIViewController 객체가 UITableView 의 내용을 알기 위해 UITableViewDataSource의 메소드들을 호출하는데 먼저 numberOfSectionInTableView를 호출해서 섹션의 갯수를 알아냄, 그 다음에 tableView를 호출해서 섹션하나에 몇개의 셀이 있는지 알아냄(섹션 갯수만큼 호출). 그 뒤 UITableViewDataSource 를 호출해서 셀의 내용을 받는다(한 화면에 보여줄 셀 갯수만큼 호출).  
---------------------------------------------------------------------------------------------------


< Navigation based application in SimpleHumanResource Architecture (SimpleHumanResource 라는 프로젝트로 Navigation based application 의 architecture를 알아보자) >
1.SimpleHumanResourceAppDelegate 안에 시스템 이벤트 처리 메소드와 아래의 것들이 있다.
UIwindow *window;  MainWindow관리(title, frame등)
UINavigationController *navigationController; MainWindow내용 전환(UIViewController들을 전환)


2.RootViewController ; 첫화면으로 이는 UIViewController, UITableViewDataSource(내용관리를 위한 프로토콜), UITableViewDelegate(이벤트를 위한 프로토콜)를 상속받은 UITableViewController을 상속받음. 즉 화면 내용, UITableView의 내용, 이벤트를 다 관리(이것은 첫화면을 UITableView를 나타내기 위해서 UITableView와 관련된 것들을 상속 받았는데, 그게 싫다면 그냥 UIViewController만 상속 받으면 된다).


3.만약 또 다른 화면을 만들고 싶다면 2번에서처럼  UIViewController를 상속받은 클래스를 만들면 된다.


2번 3번에서 만든 여러개의 화면이 공유하는 데이터나 내용은 1번의 SimpleHumanResourceAppDelegate에 넣으면 된다. [[UIApplication SharedApplication] delegate]를 사용하면 공유 정보리스트 중 SimpleHumanResourceAppDelegate를 리턴하게 된다.


UIViewController에는 IBOutlet UIView * view를 속성을 가지고 있다. UITableViewController는 IBOulet UITableView* tableView 를 가지고 있다. 그렇기 때문에 RootViewController는 이 속성을 자동으로 가지게 된다.




Outlet과 ReferenceOutlet의 차이는? Referencing Outlet 이 주소값을 받을 속성들.
----------------------------------------------------------------------------------------------------


<JSON>
서버나 클라이언트가 각각 구성된 언어가 다르기 때문에 특정 객체를 넘겨줄때 사용하는 것으로 원래는 xml을 사용했는데 xml 이 복잡하기에 JSON을 웹에서 많이 사용한다.
예를 들어 서버는 python으로 개발이 됐는데 client 는 objective-c로 된 어플을 사용중이라면 데이터 교환을 위한 통일된 형태가 필요하다. 이럴 때 사용되는 데이터 교환의 표준이 xml. 
그러면 xml을 개발자들이 잘 안쓰는 이유? xml 파싱하기가 쉽지 않아서
그래서 표준은 아직 아니지만 형식을 가진 문자열인 JSON 을 많이 사용한다. 이렇게 JSON 문자열로 서버에서 클라이언트로 데이터를 보낸다.
http://www.json.org/

Friday, March 25, 2011

iphone 개발 수업 3주차

3/25
< Collection >
-객체들의 주소 저장
-크기가 가변
-검색, 삭제, 수정이 쉽다 (삭제, 수정, 추가 가능한 것들은 mutable이 들어간 클래스들).
NSSet <- NSMutableSet 이 상속 : 삽입한 순서와 저장 순서가 다름, 객체의 중복 저장이 안된다.
NSArray <- NSMutableArray 이 상속 : 포인터 배열, 삽입순서와 저장한 순서가 같다. 중복 저장 가능. 배열대신 사용하면 편리하다.
NSDictionary <- NSMutableDictionary 상속 :  key 값으로 value의 검색이 가능.
아래 그림은 12시 부터 시계 방향으로 NSSet, NSArray, NSDictionary 의 클래스 설명.


그 위의 객체에 이름이 objects로 끝나는 메소드를 사용하려면 마지막 인자로 반드시 nil 을 넣어줘야 한다.
NSDictionary의 key 는 중복이 안되는데 이는 사실 NSSet 으로 관리한다. 그렇기 때문에 key를 꺼낼때 NSSet 이 ordering 한 순서로 나온다.


클래스의 메소드가 - 이면 반드시 alloc을 해서 객체를 생성해서 사용해야 하는것이고, + 로 된 메소드는 클래스 메소드로서 객체 생성 없이 클래스 이름으로 사용할 수 있다. 그리고 + 으로 되어 있으면 autorelease 되어 진다. 그럼 뭘 사용해야 하느냐? 그건 선택 나름.


다시 한번 1주차의 마지막에 언급된 architecture와 life cycle 그리고 2주차의 view-based application 을 읽고 이해하길 바란다.
-------------------------------------------------------------------------------------------------


<Notification>
노티피케이션이 필요할 때 :
1.  2주차에서 마지막에 나온 예 MyPickerViewDelegate예제를 보면 InstaTwitViewController는 그 안의 객체인 MyPickerViewDelegate의 메모리 주소를 알고 있지만 반대로 MyPickerViewDelegate는 InstaTwitViewController 의 메모리 위치를 알지 못한다. 그렇기 때문에 InstaTwitViewController의 메소드를 사용할수가 없다. 이럴 때 노티피케이션을 사용하면 해결, 곧 사용하고자 하는 객체의 메모리 주소를 모를 때 사용
2. 이벤트 발생시 동시에 여러개 메소드를 호출할때
3. 호출되는 객체가 무엇이지 모를 때
예를 들어 MainWindow에 버튼이 있을때 그 버튼을 누를 때 객체 A,B,C 의 메소드가 동시에 실행되어져야 할때, 혹은 어떤 객체의 메소드가 호출되는지 모를때 노티피케이션을 사용한다.


이는 InstaTwitViewController객체가 NSNotificationCenter 객체에게 NSPickerView 선택시 알려달라고 요청함. 그러면 NSNotification이 백그라운드로 감시하다가 이벤트가 발생하면 InstaTwitViewContoller에게 알려준다.
그러면 통보하고자 하는 MyPickerViewDelegate에서 NSNotificationCenter에 통보하는 실행문을 넣는다. 그러면 MyPickerViewDelegate에서 특정 메소드가 호출될때 NSNotificationCenter에 통보를 하고 이 객체가 다시 InstaTwitViewController 객체에 NSNotification 객체(이 안에 정보가 다 있다)통보가 된다.


이 순서는 NSNotificationCenter 를 InstaTwitViewController객체 안에 생성하고 등록한다. 그러면 이벤트가 발생하였을 때 NSNotificationCenter가 InstaTwitViewController객체에게 통보를 하게 된다. 
생성 : NSNotification 은 어플 실행시 생성, 딱 하나만 생성, 리눅스의 데몬처럼 백그라운드로 실행, [NSNotificationCenter defaultCenter] 하면 NSNotification이 리턴된다.
등록 : [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(UiUpdate) name:@"name" object:nil userInfo:nil] ; self, 즉 자신 객체를 등록하고 이벤트 발생시 호출될 메소드는 UiUpdate라는 메소드이고(@selector는 메소드의 주소를 return)  이름은 name으로 하고 object는 nil 이다(object에는 주소를 넣을 수 있다, 이러면 NSNotificationCenter 객체가 이벤트 발생을 통보시, 즉 메소드 호출 시 그 주소를 인자로 넘긴다) 라는 의미.
통보 : [[NSNotificationCenter defaultCenter] postNotificationName:@"PickerViewDidChanged" object:self userInfo:nil] ; 통보하는 곳의 이름은 PickerViewDidChaged이고 self, 나 자신을 넘기고 더 넘기고자 하는 더 필요한 데이터는 없다라는 의미


원래 특정 이벤트의 발생을 감시하는 것은 UIApplication이 하는 일이였으나 UIApplication이 감시하는 이벤트는 시스템적인 이벤트, 그러니까 버튼이 눌리는 것 같은 이벤트, 그러나 나머지 이벤트 즉 시스템적인 이벤트를 제외한 이벤트는 NSNotificationCenter가 모니터링한다. 
-----------------------------------------------------------------------------------------------


속성을 다른 객체에서 사용하려면 1. set,get 메소드를 정의하거나 2. @property로 선언하거나 3. keyofvalue dictionary를 이용한다.


<Key Value Dictionary>
일반적으로 객체는 NSObject를 상속하는데 NSObject 클래스에는 NSMutableDictionary가 있어서 key 값으로 NSObject를 상속받은 클래스의 속성을, value로는 그 속성의 속성값(그러니까 속성안에 들어가 있는 값)을 가지고 있다. 이를 이용하면 코딩이 짧아짐.


그런데 이 key value observing이 꼭 대입이 되는 것은 아니다. 예를 들어 IBOulet으로 선언된 속성(즉 interface builder로 만든 view(xml에 정의된)의 주소를 넣을 속성)는 반드시 set,get 메소드를 만들거나 property로 선언해서 사용해야 한다.


사용방법 : NSObject 를 상속받은 클래스 MyCandle이라는 것이 있을때 keyofvalue Dictionary 를 사용하려면 [MyCandle valueForKey:@"candleState"];는 property로 사용할때의 MyCandle.candleState와 동일한 의미, [MyCandle setValue:NO forKey:@"candleState"];  는 MyCandle.candleState = NO; 과 동일.


<Key Value Observing>
NSObject를 상속받은 클래스 MyCandle의 속성과 keyofvalue dictionary는 MyCandle 이 감시하면서 그 두값을 같게 맞추는데 둘중 하나가 변했을때 알려달라, 곧 메소드를 호출해 달라. 그런데 Notification과는 달리 호출되는 메소드 이름(observeValueForKeyPath)이 정해져 있다. 그래서 메소드를 @selector로 해서 인자로 넘길일은 없다.


설정 : [MyCandle addObserver:self forKeyPath:@"candleState" option:NSKeyValueObservingOptionNew|NSKeyValueObservingOld context:nil]; candleState속성이 수정시 self, 즉 나 자신에게 수정된 값이 뭔지(NSKeyValueObservingOptionNew), 그리고 예전값이 뭐였는지(NSKeyValueObservingOld) 그리고 통보할때 nil(지금은 nil이기 때문에 아무것도 없다)을 전달하면서 알려달라라는 의미.
호출되는 메소드 : -(void)observeValueForKeyPath:(NSString*)keyPath ofObject:(id)object change:(NSDictionary*)change context:(void*)context ; keyPath는 값이 수정된 속성이름, object는 통보자의 주소, change에는 바꾸기 전의 값과 바뀐후의 값이 dictionary(NSKeyValueChangeNewValue와 NSKeyValueChangeOldKey를 key로 갖는다)로, context 는 addObserver호출시 전달했던 인자.


등록시 option의 인자를 NSKeyValueObservingOptionInitial 은 원래 등록을 하면 감시가 시작되는 것이 아니라 등록하는 메소드(그러니까 등록 statement가 있는 메소드)가 끝나야 호출이 되는데(왜냐면 single thread이기 때문에) 이 option 을 사용하면 등록하는 순간 바로 monitoring 을 시작한다. 


notification과 key value observing 이랑 유사한데 그럼 언제 key value observing  를 사용하느냐? 값이 바뀌었을 때 통보할 때


이벤트가 발생했을때 호출되는 메소드는  return 값이 없다.

sqlite3

sql이 필요하게 됐다. sqlite3를 쓰기로 한다. 그닥 큰 db가 아니라서. 

sqlite3 설치
다운받고 그냥 install (configure=>make=>make check=>make install), 끝

sqlite3 사용법
내가 사용하는 건 굉장히 단순한 select문만 필요한거라.. 근데 첨에 하면 어떻게 실행시키고 어떻게 db를 만드는지 조차 생소한다. 알고나면 아.. 쉽네.. 
주의할건 special command. cvs file을 table로 load 할려면 special command의 .import 를 사용할 것. 다만 먼저 .separator를 할것.

python으로 연동하기