簡(jiǎn)述類(lèi)目category優(yōu)點(diǎn)和缺點(diǎn)
優(yōu)點(diǎn):
不需要通過(guò)增加子類(lèi)而增加現(xiàn)有類(lèi)的行為(方法),且類(lèi)目中的方法與原始類(lèi)方法基本沒(méi)有區(qū)別;
通過(guò)類(lèi)目可以將龐大一個(gè)類(lèi)的方法進(jìn)行劃分,從而便于代碼的日后的維護(hù)、更新以及提高代碼的閱讀性;
缺點(diǎn):
無(wú)法向類(lèi)目添加實(shí)例變量,如果需要添加實(shí)例變量,只能通過(guò)定義子類(lèi)的方式;
類(lèi)目中的方法與原始類(lèi)以及父類(lèi)方法相比具有更高優(yōu)先級(jí),如果覆蓋父類(lèi)的方法,可能導(dǎo)致super消息的斷裂。因此,最好不要覆蓋原始類(lèi)中的方法。
鍵值編碼KVC
鍵值編碼是一種間接訪問(wèn)對(duì)象的屬性使用字符串來(lái)標(biāo)識(shí)屬性,而不是通過(guò)調(diào)用存取方法,直接或通過(guò)實(shí)例變量訪問(wèn)的機(jī)制,非對(duì)象類(lèi)型的變量將被自動(dòng)封裝或者解封成對(duì)象,很多情況下會(huì)簡(jiǎn)化程序代碼;
KVC的缺點(diǎn):一旦使用 KVC 你的編譯器無(wú)法檢查出錯(cuò)誤,即不會(huì)對(duì)設(shè)置的鍵、鍵路徑進(jìn)行錯(cuò)誤檢查,且執(zhí)行效率要低于合成存取器方法和自定的 setter 和 getter 方法。因?yàn)槭褂?KVC 鍵值編碼,它必須先解析字符串,然后在設(shè)置或者訪問(wèn)對(duì)象的實(shí)例變量。
鍵值觀察KVO
鍵值觀察機(jī)制是一種能使得對(duì)象獲取到其他對(duì)象屬性變化的通知 ,極大的簡(jiǎn)化了代碼。
實(shí)現(xiàn) KVO 鍵值觀察模式,被觀察的對(duì)象必須使用 KVC 鍵值編碼來(lái)修 改它的實(shí)例變量,這樣才能被觀察者觀察到。因此,KVC是KVO的基礎(chǔ)。
KVC機(jī)制通過(guò)key找到value的原理
當(dāng)通過(guò)KVC調(diào)用對(duì)象時(shí),比如:[self valueForKey:@”someKey”]時(shí),程序會(huì)自動(dòng)試圖通過(guò)下面幾種不同的方式解析這個(gè)調(diào)用。
首先查找對(duì)象是否帶有 someKey 這個(gè)方法,如果沒(méi)找到,會(huì)繼續(xù)查找對(duì)象是否帶有someKey這個(gè)實(shí)例變量(iVar),如果還沒(méi)有找到,程序會(huì)繼續(xù)試圖調(diào)用 -(id) valueForUndefinedKey:這個(gè)方法。如果這個(gè)方法還是沒(méi)有被實(shí)現(xiàn)的話,程序會(huì)拋出一個(gè)NSUndefinedKeyException異常錯(cuò)誤。
補(bǔ)充:KVC查找方法的時(shí)候,不僅僅會(huì)查找someKey這個(gè)方法,還會(huì)查找getsomeKey這個(gè)方法,前面加一個(gè)get,或者_(dá)someKey以_getsomeKey這幾種形式。同時(shí),查找實(shí)例變量的時(shí)候也會(huì)不僅僅查找someKey這個(gè)變量,也會(huì)查找_someKey這個(gè)變量是否存在。
設(shè)計(jì)valueForUndefinedKey:方法的主要目的是當(dāng)你使用-(id)valueForKey方法從對(duì)象中請(qǐng)求值時(shí),對(duì)象能夠在錯(cuò)誤發(fā)生前,有最后的機(jī)會(huì)響應(yīng)這個(gè)請(qǐng)求。
#include與#import的區(qū)別、#import 與@class 的區(qū)別
include 和import其效果相同,都是查詢(xún)類(lèi)中定義的行為(方法);
import不會(huì)引起交叉編譯,確保頭文件只會(huì)被導(dǎo)入一次;
@class 的表明,只定 義了類(lèi)的名稱(chēng),而具體類(lèi)的行為是未知的,一般用于.h 文件;
@class 比#import 編譯效率更高。
此外@class 和#import 的主要區(qū)別在于解決引用死鎖的問(wèn)題。
UITableViewCell上有個(gè)UILabel,顯示NSTimer實(shí)現(xiàn)的秒表時(shí)間,手指滾動(dòng)cell過(guò)程中,label是否刷新,為什么?
這是否刷新取決于timer加入到Run Loop中的Mode是什么。Mode主要是用來(lái)指定事件在運(yùn)行循環(huán)中的優(yōu)先級(jí)的,分為:
NSDefaultRunLoopMode(kCFRunLoopDefaultMode):默認(rèn),空閑狀態(tài)
UITrackingRunLoopMode:ScrollView滑動(dòng)時(shí)會(huì)切換到該Mode
UIInitializationRunLoopMode:run loop啟動(dòng)時(shí),會(huì)切換到該mode
NSRunLoopCommonModes(kCFRunLoopCommonModes):Mode集合
蘋(píng)果公開(kāi)提供的Mode有兩個(gè):NSDefaultRunLoopMode(kCFRunLoopDefaultMode)
NSRunLoopCommonModes(kCFRunLoopCommonModes)
在編程中:如果我們把一個(gè)NSTimer對(duì)象以NSDefaultRunLoopMode(kCFRunLoopDefaultMode)添加到主運(yùn)行循環(huán)中的時(shí)候, ScrollView滾動(dòng)過(guò)程中會(huì)因?yàn)閙ode的切換,而導(dǎo)致NSTimer將不再被調(diào)度。當(dāng)我們滾動(dòng)的時(shí)候,也希望不調(diào)度,那就應(yīng)該使用默認(rèn)模式。但是,如果希望在滾動(dòng)時(shí),定時(shí)器也要回調(diào),那就應(yīng)該使用common mode。
對(duì)于單元格重用的理解
- 當(dāng)屏幕上滑出屏幕時(shí),系統(tǒng)會(huì)把這個(gè)單元格添加到重用隊(duì)列中,等待被重用,當(dāng)有新單元從屏幕外滑入屏幕內(nèi)時(shí),從重用隊(duì)列中找看有沒(méi)有可以重用的單元格,若有,就直接用,沒(méi)有就重新創(chuàng)建一個(gè)。
線程與進(jìn)程的區(qū)別和聯(lián)系?
- 一個(gè)程序至少要有進(jìn)城,一個(gè)進(jìn)程至少要有一個(gè)線程.
- 進(jìn)程:資源分配的最小獨(dú)立單元,進(jìn)程是具有一定獨(dú)立功能的程序關(guān)于某個(gè)數(shù)據(jù)集合上的一次運(yùn)行活動(dòng),進(jìn)程是系統(tǒng)進(jìn)行資源分配和調(diào)度的一個(gè)獨(dú)立單位.
- 線程:進(jìn)程下的一個(gè)分支,是進(jìn)程的實(shí)體,是CPU調(diào)度和分派的基本單元,它是比進(jìn)程更小的能獨(dú)立運(yùn)行的基本單位,線程自己基本不擁有系統(tǒng)資源,只擁有一點(diǎn)在運(yùn)行中必不可少的資源(程序計(jì)數(shù)器、一組寄存器、棧),但是它可與同屬一個(gè)進(jìn)程的其他線程共享進(jìn)程所擁有的全部資源。
- 進(jìn)程和線程都是由操作系統(tǒng)所體會(huì)的程序運(yùn)行的基本單元,系統(tǒng)利用該基本單元實(shí)現(xiàn)系統(tǒng)對(duì)應(yīng)用的并發(fā)性。
- 進(jìn)程和線程的主要差別在于它們是不同的操作系統(tǒng)資源管理方式。進(jìn)程有獨(dú)立的地址空間,一個(gè)進(jìn)程崩潰后,在保護(hù)模式下不會(huì)對(duì)其它進(jìn)程產(chǎn)生影響,而線程只是一個(gè)進(jìn)程中的不同執(zhí)行路徑。線程有自己的堆棧和局部變量,但線程之間沒(méi)有單獨(dú)的地址空間,一個(gè)線程死掉就等于整個(gè)進(jìn)程死掉,所以多進(jìn)程的程序要比多線程的程序健壯,但在進(jìn)程切換時(shí),耗費(fèi)資源較大,效率要差一些。
但對(duì)于一些要求同時(shí)進(jìn)行并且又要共享某些變量的并發(fā)操作,只能用線程,不能用進(jìn)程。
TCP和UDP的區(qū)別于聯(lián)系
- TCP為傳輸控制層協(xié)議,為面向連接、可靠的、點(diǎn)到點(diǎn)的通信;
- UDP為用戶數(shù)據(jù)報(bào)協(xié)議,非連接的不可靠的點(diǎn)到多點(diǎn)的通信;
- TCP側(cè)重可靠傳輸,UDP側(cè)重快速傳輸。
TCP連接的三次握手
- 第一次握手:客戶端發(fā)送syn包(syn=j)到服務(wù)器,并進(jìn)入SYN_SEND狀態(tài),等待服務(wù)器確認(rèn);
- 第二次握手:服務(wù)器收到syn包,必須確認(rèn)客戶的SYN(ack=j+1),同時(shí)自己也發(fā)送一個(gè)SYN包,即SYN+ACK包,此時(shí)服務(wù)器進(jìn)入SYN+RECV狀態(tài);
- 第三次握手:客戶端收到服務(wù)器的SYN+ACK包,向服務(wù)器發(fā)送確認(rèn)包ACK(ack=k+1),此發(fā)送完畢,客戶端和服務(wù)器進(jìn)入ESTABLISHED狀態(tài),完成三次狀態(tài)。
Scoket連接和HTTP連接的區(qū)別:
- HTTP協(xié)議是基于TCP連接的,是應(yīng)用層協(xié)議,主要解決如何包裝數(shù)據(jù)。
- Socket是對(duì)TCP/IP協(xié)議的封裝,Socket本身并不是協(xié)議,而是一個(gè)調(diào)用接口(API),通過(guò)Socket,我們才能使用TCP/IP協(xié)議。
- HTTP連接:短連接,客戶端向服務(wù)器發(fā)送一次請(qǐng)求,服務(wù)器響應(yīng)后連接斷開(kāi),節(jié)省資源。服務(wù)器不能主動(dòng)給客戶端響應(yīng)(除非采用HTTP長(zhǎng)連接技術(shù)),iPhone主要使用類(lèi)NSURLConnection。
- Socket連接:長(zhǎng)連接,客戶端跟服務(wù)器端直接使用Socket進(jìn)行連接,沒(méi)有規(guī)定連接后斷開(kāi),因此客戶端和服務(wù)器段保持連接通道,雙方可以主動(dòng)發(fā)送數(shù)據(jù),一般多用于游戲.Socket默認(rèn)連接超時(shí)時(shí)間是30秒,默認(rèn)大小是8K(理解為一個(gè)數(shù)據(jù)包大?。?/li>
如何進(jìn)行真機(jī)調(diào)試
- 1.首先需要用鑰匙串創(chuàng)建一個(gè)鑰匙(key);
- 2.將鑰匙串上傳到官網(wǎng),獲取iOS Development證書(shū);
- 3.創(chuàng)建App ID即我們應(yīng)用程序中的Boundle ID;
- 4.添加Device ID即UDID;
- 5.通過(guò)勾選前面所創(chuàng)建的證書(shū):App ID、Device ID;
- 6.生成mobileprovision文件;
- 7.先決條件:申請(qǐng)開(kāi)發(fā)者賬號(hào) 99美刀
APP發(fā)布的上架流程
- 1.登錄應(yīng)用發(fā)布網(wǎng)站添加應(yīng)用信息;
- 2.下載安裝發(fā)布證書(shū);
- 3.選擇發(fā)布證書(shū),使用Archive編譯發(fā)布包,用Xcode將代碼(發(fā)布包)上傳到服務(wù)器;
- 4.等待審核通過(guò);
- 5.生成IPA:菜單欄->Product->Archive.
網(wǎng)絡(luò)推送通知原理
首先應(yīng)用發(fā)送通知,系統(tǒng)彈出提示框詢(xún)問(wèn)用戶是否允許,當(dāng)用戶允許后向蘋(píng)果服務(wù)器(APNS)請(qǐng)求deviceToken,并由蘋(píng)果服務(wù)器發(fā)送給自己的應(yīng)用,自己的應(yīng)用將DeviceToken發(fā)送自己的服務(wù)器,自己服務(wù)器想要發(fā)送網(wǎng)絡(luò)推送時(shí)將deviceToken以及想要推送的信息發(fā)送給蘋(píng)果服務(wù)器,蘋(píng)果服務(wù)器將信息發(fā)送給應(yīng)用。
網(wǎng)絡(luò)七層協(xié)議
- 應(yīng)用層:1.用戶接口、應(yīng)用程序;2.Application典型設(shè)備:網(wǎng)關(guān);3.典型協(xié)議、標(biāo)準(zhǔn)和應(yīng)用:TELNET、FTP、HTTP
- 表示層:1.數(shù)據(jù)表示、壓縮和加密presentation2.典型設(shè)備:網(wǎng)關(guān)3.典型協(xié)議、標(biāo)準(zhǔn)和應(yīng)用:ASCLL、PICT、TIFF、JPEG|MPEG4.表示層相當(dāng)于一個(gè)東西的表示,表示的一些協(xié)議,比如圖片、聲音和視頻MPEG。
- 會(huì)話層:1.會(huì)話的建立和結(jié)束;2.典型設(shè)備:網(wǎng)關(guān);3.典型協(xié)議、標(biāo)準(zhǔn)和應(yīng)用:RPC、SQL、NFS、X WINDOWS、ASP
- 傳輸層:1.主要功能:端到端控制Transport;2.典型設(shè)備:網(wǎng)關(guān);3.典型協(xié)議、標(biāo)準(zhǔn)和應(yīng)用:TCP、UDP、SPX
- 網(wǎng)絡(luò)層:1.主要功能:路由、尋址Network;2.典型設(shè)備:路由器;3.典型協(xié)議、標(biāo)準(zhǔn)和應(yīng)用:IP、IPX、APPLETALK、ICMP;
- 數(shù)據(jù)鏈路層:1.主要功能:保證無(wú)差錯(cuò)的疏忽鏈路的data link;2.典型設(shè)備:交換機(jī)、網(wǎng)橋、網(wǎng)卡;3.典型協(xié)議、標(biāo)準(zhǔn)和應(yīng)用:802.2、802.3ATM、HDLC、FRAME RELAY;
- 物理層:1.主要功能:傳輸比特流Physical;2.典型設(shè)備:集線器、中繼器3.典型協(xié)議、標(biāo)準(zhǔn)和應(yīng)用:V.35、EIA/TIA-232.
對(duì)NSUserDefaults的理解
- NSUserDefaults:系統(tǒng)提供的一種存儲(chǔ)數(shù)據(jù)的方式,主要用于保存少量的數(shù)據(jù),默認(rèn)存儲(chǔ)到library下的Preferences文件夾。
SDWebImage原理
調(diào)用類(lèi)別的方法:
- 從內(nèi)存中(字典)找圖片(當(dāng)這個(gè)圖片在本次程序加載過(guò)),找到直接使用;
- 從沙盒中找,找到直接使用,緩存到內(nèi)存。
- 從網(wǎng)絡(luò)上獲取,使用,緩存到內(nèi)存,緩存到沙盒。
對(duì)于Run Loop的理解
- RunLoop,是多線程的法寶,即一個(gè)線程一次只能執(zhí)行一個(gè)任務(wù),執(zhí)行完任務(wù)后就會(huì)退出線程。主線程執(zhí)行完即時(shí)任務(wù)時(shí)會(huì)繼續(xù)等待接收事件而不退出。非主線程通常來(lái)說(shuō)就是為了執(zhí)行某一任務(wù)的,執(zhí)行完畢就需要?dú)w還資源,因此默認(rèn)是不運(yùn)行RunLoop的;
- 每一個(gè)線程都有其對(duì)應(yīng)的RunLoop,只是默認(rèn)只有主線程的RunLoop是啟動(dòng)的,其它子線程的RunLoop默認(rèn)是不啟動(dòng)的,若要啟動(dòng)則需要手動(dòng)啟動(dòng);
在一個(gè)單獨(dú)的線程中,如果需要在處理完某個(gè)任務(wù)后不退出,繼續(xù)等待接收事件,則需要啟用RunLoop; - NSRunLoop提供了一個(gè)添加NSTimer的方法,可以指定Mode,如果要讓任何情況下都回調(diào),則需要設(shè)置Mode為Common模式;
- 實(shí)質(zhì)上,對(duì)于子線程的runloop默認(rèn)是不存在的,因?yàn)樘O(píng)果采用了懶加載的方式。如果我們沒(méi)有手動(dòng)調(diào)用[NSRunLoop currentRunLoop]的話,就不會(huì)去查詢(xún)是否存在當(dāng)前線程的RunLoop,也就不會(huì)去加載,更不會(huì)創(chuàng)建。
SQLite中常用的SQL語(yǔ)句
- 創(chuàng)建表:creat table 表名 (字段名 字段數(shù)據(jù)類(lèi)型 是否為主鍵, 字段名 字段數(shù)據(jù)類(lèi)型, 字段名 字段數(shù)據(jù)類(lèi)型...);
-
增: insert into 表名 (字段1, 字段2...) values (值1, 值2...);
insert into Strdents (姓名,性別,出生日期) values ('開(kāi)心朋朋','男','1980/6/15') -
刪: delete from 表名 where 字段 = 值;
delete from a where name='開(kāi)心朋朋'(刪除表a中列值為開(kāi)心朋朋的行) -
改:update <表名> set <列名=更新值> [where <更新條件>]
update tongxunlu set 年齡=18 where 姓名='藍(lán)色小名' - **查 **:select <列名> from <表名> [where <查詢(xún)條件表達(dá)試>] [order by <排序的列名>[asc或desc]]
select * from a
內(nèi)存的使用和優(yōu)化的注意事項(xiàng)
重用問(wèn)題:如UITableViewCells、UICollectionViewCells、UITableViewHeaderFooterViews設(shè)置正確的reuseIdentifier,充分重用;
盡量把views設(shè)置為不透明:當(dāng)opque為NO的時(shí)候,圖層的半透明取決于圖片和其本身合成的圖層為結(jié)果,可提高性能;
不要使用太復(fù)雜的XIB/Storyboard:載入時(shí)就會(huì)將XIB/storyboard需要的所有資源,包括圖片全部載入內(nèi)存,即使未來(lái)很久才會(huì)使用。那些相比純代碼寫(xiě)的延遲加載,性能及內(nèi)存就差了很多;
選擇正確的數(shù)據(jù)結(jié)構(gòu):學(xué)會(huì)選擇對(duì)業(yè)務(wù)場(chǎng)景最合適的數(shù)組結(jié)構(gòu)是寫(xiě)出高效代碼的基礎(chǔ)。比如,數(shù)組: 有序的一組值。使用索引來(lái)查詢(xún)很快,使用值查詢(xún)很慢,插入/刪除很慢。字典: 存儲(chǔ)鍵值對(duì),用鍵來(lái)查找比較快。集合: 無(wú)序的一組值,用值來(lái)查找很快,插入/刪除很快。gzip/zip壓縮:當(dāng)從服務(wù)端下載相關(guān)附件時(shí),可以通過(guò)gzip/zip壓縮后再下載,使得內(nèi)存更小,下載速度也更快。
延遲加載:對(duì)于不應(yīng)該使用的數(shù)據(jù),使用延遲加載方式。對(duì)于不需要馬上顯示的視圖,使用延遲加載方式。比如,網(wǎng)絡(luò)請(qǐng)求失敗時(shí)顯示的提示界面,可能一直都不會(huì)使用到,因此應(yīng)該使用延遲加載。
數(shù)據(jù)緩存:對(duì)于cell的行高要緩存起來(lái),使得reload數(shù)據(jù)時(shí),效率也極高。而對(duì)于那些網(wǎng)絡(luò)數(shù)據(jù),不需要每次都請(qǐng)求的,應(yīng)該緩存起來(lái),可以寫(xiě)入數(shù)據(jù)庫(kù),也可以通過(guò)plist文件存儲(chǔ)。
處理內(nèi)存警告:一般在基類(lèi)統(tǒng)一處理內(nèi)存警告,將相關(guān)不用資源立即釋放掉重用大開(kāi)銷(xiāo)對(duì)象:一些objects的初始化很慢,比如NSDateFormatter
和NSCalendar
,但又不可避免地需要使用它們。通常是作為屬性存儲(chǔ)起來(lái),防止反復(fù)創(chuàng)建。
避免反復(fù)處理數(shù)據(jù):許多應(yīng)用需要從服務(wù)器加載功能所需的常為JSON或者XML格式的數(shù)據(jù)。在服務(wù)器端和客戶端使用相同的數(shù)據(jù)結(jié)構(gòu)很重要;
使用Autorelease Pool:在某些循環(huán)創(chuàng)建臨時(shí)變量處理數(shù)據(jù)時(shí),自動(dòng)釋放池以保證能及時(shí)釋放內(nèi)存;
正確選擇圖片加載方式:詳情閱讀細(xì)讀UIImage加載方式
堆和棧的區(qū)別
管理方式:
對(duì)于棧來(lái)講,是由編譯器自動(dòng)管理,無(wú)需我們手工控制;對(duì)于堆來(lái)說(shuō),釋放工作由程序員控制,容易產(chǎn)生memory leak。
申請(qǐng)大小:
棧:棧頂?shù)牡刂泛蜅5淖畲笕萘渴窍到y(tǒng)預(yù)先規(guī)定好的,如果申請(qǐng)的空間超過(guò)棧的剩余空間時(shí),將提示overflow。因此,能從棧獲得的空間較小。
堆:堆是向高地址擴(kuò)展的數(shù)據(jù)結(jié)構(gòu),是不連續(xù)的內(nèi)存區(qū)域。這是由于系統(tǒng)是用鏈表來(lái)存儲(chǔ)的空閑內(nèi)存地址的,自然是不連續(xù)的,而鏈表的遍歷方向是由低地址向高地址。堆的大小受限于計(jì)算機(jī)系統(tǒng)中有效的虛擬內(nèi)存。由此可見(jiàn),堆獲得的空間比較靈活,也比較大。
碎片問(wèn)題:
對(duì)于堆來(lái)講,頻繁的new/delete勢(shì)必會(huì)造成內(nèi)存空間的不連續(xù),從而造成大量的碎片,使程序效率降低。對(duì)于棧來(lái)講,則不會(huì)存在這個(gè)問(wèn)題,因?yàn)闂J窍冗M(jìn)后出的隊(duì)列,他們是如此的一一對(duì)應(yīng),以至于永遠(yuǎn)都不可能有一個(gè)內(nèi)存塊從棧中間彈出