青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

posts - 319, comments - 22, trackbacks - 0, articles - 11
  C++博客 :: 首頁 :: 新隨筆 :: 聯(lián)系 :: 聚合  :: 管理

很多程序有這樣的功能,雙擊某個圖片可以打開源文件,右鍵菜單中的Show in Finder功能,Cocoa中對這塊支持較好,有現(xiàn)成的方法:

[[NSWorkspace sharedWorkspace] openFile:fileName];

[[NSWorkspace sharedWorkspace] selectFile:fileName inFileViewerRootedAtPath:path];  // 如果只打開目錄不需要選中具體文件,fileName可為nil。

posted @ 2013-01-07 23:23 RTY 閱讀(664) | 評論 (0)編輯 收藏

http://www.cnbeta.com/articles/219634.htm

感謝GZX的投遞
今天剛剛收到Windows 8商店的提示,掃雷可以更新了,于是興致勃勃的下載最新版的Windows 8掃雷,截圖給大家看。
從開始屏幕上看,掃雷的應(yīng)用磁帖并沒有發(fā)生太大的變化。


但是打開應(yīng)用之后,就會發(fā)現(xiàn)有了不一樣的地方。
在主題部分,你將會看到新的主題“傳統(tǒng)主題”。

當(dāng)你點擊了傳統(tǒng)主題后,游戲選項卡部分將會變?yōu)閭鹘y(tǒng)的掃雷樣式。

隨意進(jìn)入一個選項卡,就可以看到我們熟悉的界面

進(jìn)入自定義模式后,我們可以看到三個選項條,分別為:長、寬以及雷數(shù),最大值如圖所示

進(jìn)入冒險模式后,我們可以發(fā)現(xiàn)與之前的版本并沒有太大變化

出現(xiàn)了廣告界面則是在“每日挑戰(zhàn)”中

打開“每日挑戰(zhàn)”,我們可以看到界面的右側(cè)多了一個廣告顯示的位置,如下圖紅框內(nèi)所示

而當(dāng)你選擇了任意一個模式后,就被強迫觀看30s的廣告

視頻緩沖階段,你會看到如下文字:“Thanks to our sponsors, this game is free(感謝我們的贊助商,本游戲完全免費)”

而觀看視頻時,它還會提示你游戲開始的時間,注意中下部
進(jìn)入游戲后,則與之前介紹的界面完全類似


這里要提示的是,每次打開掃雷應(yīng)用的“每日挑戰(zhàn)”,你只需要觀看一次視頻廣告(每次的廣告均有所不同),就可以體驗全部的三個模式
 
那么,你準(zhǔn)備好升級你的掃雷了么?

posted @ 2012-12-26 10:32 RTY 閱讀(417) | 評論 (0)編輯 收藏

UITabBarController是選項卡欄導(dǎo)航控制器,顯示效果是在頁面底部有多個選項卡,通過點擊不同選項卡可以在不同的ViewController之間進(jìn)行切換。


這種對象的層次結(jié)構(gòu)至少包含6個對象:

一個UITabBarController;

兩個UIViewController;

一個UITabBar;

兩個UITabBarItem;


UITabBarController 是選項卡欄視圖控制器,UITabBar是底部兩個UITabBarItem的容器,管理兩個UITabBarItem,每個UITabBarItem對 應(yīng)一個UIViewController,然后每個UIViewController都有自己的視圖和視圖控制器。


UITabBarController中有一個viewControllers屬性,這是一個NSArray,包含選項卡控制器的視圖控制器


下面來用代碼創(chuàng)建一個UITabBarController:

下面是工程結(jié)構(gòu):

首先創(chuàng)建兩個帶xib文件的ViewController,分別為FirstViewController和SecondViewController

然后在AppDelegate.h中聲明@property (strong,nonatomic) UITabBarController *tabBarController;,并添加協(xié)議UITabBarControllerDelegate


在.m中實現(xiàn)如下代碼:

  1. - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions  
  2. {  
  3.     self.window = [[[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]] autorelease];  
  4.     // Override point for customization after application launch.  
  5.      
  6.     //第一個tab的viewController  
  7.     FirstViewController *firstViewController = [[FirstViewController alloc]init];  
  8.      
  9.     //如果在這里指定tabitem標(biāo)題,則在FirstViewController中指定self.tabBarItem.title則不生效     
  10.     firstViewController.title = @"First view";  
  11.      
  12.     UITabBarItem *firstItem = [[UITabBarItem alloc]initWithTitle:@"First" image:nil tag:1];  
  13.     [firstItem setFinishedSelectedImage:[UIImage imageNamed:@"p1"] withFinishedUnselectedImage:[UIImage imageNamed:@"p1_f"]];  
  14.     firstViewController.tabBarItem = firstItem;  
  15.      
  16.      
  17.     SecondViewController *secondViewController = [[SecondViewController alloc]init];  
  18.      
  19.     //構(gòu)建TabBarItem  
  20.     UITabBarItem *secondItem = [[UITabBarItem alloc]initWithTitle:@"Second" image:nil tag:2];  
  21.      
  22.     //設(shè)置選中和非選中狀態(tài)下的圖片  
  23.     [secondItem setFinishedSelectedImage:[UIImage imageNamed:@"p2_f"] withFinishedUnselectedImage:[UIImage imageNamed:@"p2"]];  
  24.     //右上角小圖標(biāo)  
  25.    [secondItem setBadgeValue:@"2"];  
  26.     //指定tabBarItem  
  27.     secondViewController.tabBarItem = secondItem;  
  28.     [secondItem release];  
  29.      
  30.     //構(gòu)建UITabBarController并指定代理為本身  
  31.     self.tabBarController = [[[UITabBarController alloc]init] autorelease];  
  32.     self.tabBarController.delegate = self;  
  33.      
  34.     //為UITabBarController添加TabBarItem  
  35.     self.tabBarController.viewControllers = [NSArray arrayWithObjects:firstViewController,secondViewController, nil];  
  36.      
  37.     [firstViewController release];  
  38.     [secondViewController release];  
  39.      
  40.     //設(shè)置選中哪個tab  
  41. //    [self.tabBarController setSelectedIndex:0];  
  42.      
  43.     //指定根視圖  
  44.     self.window.rootViewController  = self.tabBarController;  
  45.      
  46.     self.window.backgroundColor = [UIColor whiteColor];  
  47.     [self.window makeKeyAndVisible];  
  48.     return YES;  
  49. }  




posted @ 2012-12-26 10:31 RTY 閱讀(1187) | 評論 (0)編輯 收藏

  在這篇文章中,我想向大家介紹如何進(jìn)行Lua程序設(shè)計。我假設(shè)大家都學(xué)過至少一門編程語言,比如Basic或C,特別是C。因為Lua的最大用途是在宿主程序中作為腳本使用的。

  Lua 的語法比較簡單,學(xué)習(xí)起來也比較省力,但功能卻并不弱。

  在Lua中,一切都是變量,除了關(guān)鍵字。請記住這句話。

I. 首先是注釋

  寫一個程序,總是少不了注釋的。
  在Lua中,你可以使用單行注釋和多行注釋。
  單行注釋中,連續(xù)兩個減號"--"表示注釋的開始,一直延續(xù)到行末為止。相當(dāng)于C++語言中的"http://"。
  多行注釋中,由"--[["表示注釋開始,并且一直延續(xù)到"]]"為止。這種注釋相當(dāng)于C語言中的"/*…*/"。在注釋當(dāng)中,"[["和"]]"是可以嵌套的。

II. Lua編程

  經(jīng)典的"Hello world"的程序總是被用來開始介紹一種語言。在Lua中,寫一個這樣的程序很簡單:
  print("Hello world")
  在Lua中,語句之間可以用分號";"隔開,也可以用空白隔開。一般來說,如果多個語句寫在同一行的話,建議總是用分號隔開。
  Lua 有好幾種程序控制語句,如:

  條件控制:if 條件 then … elseif 條件 then … else … end
  While循環(huán):while 條件 do … end
  Repeat循環(huán):repeat … until 條件
  For循環(huán):for 變量 = 初值,終點值,步進(jìn) do … end
  For循環(huán):for 變量1,變量2,… ,變量N in表或枚舉函數(shù) do … end

  注意一下,for的循環(huán)變量總是只作用于for的局部變量,你也可以省略步進(jìn)值,這時候,for循環(huán)會使用1作為步進(jìn)值。
  你可以用break來中止一個循環(huán)。
  如果你有程序設(shè)計的基礎(chǔ),比如你學(xué)過Basic,C之類的,你會覺得Lua也不難。但Lua有幾個地方是明顯不同于這些程序設(shè)計語言的,所以請?zhí)貏e注意。

  .語句塊
    語句塊在C++中是用"{"和"}"括起來的,在Lua中,它是用do 和 end 括起來的。比如: 
    do print("Hello") end
    你可以在 函數(shù) 中和 語句塊 中定局部變量。

  .賦值語句
    賦值語句在Lua被強化了。它可以同時給多個變量賦值。
    例如:
    a,b,c,d=1,2,3,4
    甚至是:
    a,b=b,a -- 多么方便的交換變量功能啊。
    在默認(rèn)情況下,變量總是認(rèn)為是全局的。假如你要定義局部變量,則在第一次賦值的時候,需要用local說明。比如:
    local a,b,c = 1,2,3 -- a,b,c都是局部變量

  .?dāng)?shù)值運算
    和C語言一樣,支持 +, -, *, /。但Lua還多了一個"^"。這表示指數(shù)乘方運算。比如2^3 結(jié)果為8, 2^4結(jié)果為16。
    連接兩個字符串,可以用".."運處符。如:
    "This a " .. "string." -- 等于 "this a string"

  .比較運算
    < > <= >= == ~=
    分別表示 小于,大于,不大于,不小于,相等,不相等
    所有這些操作符總是返回true或false。
    對于Table,F(xiàn)unction和Userdata類型的數(shù)據(jù),只有 == 和 ~=可以用。相等表示兩個變量引用的是同一個數(shù)據(jù)。比如:
    a={1,2}
    b=a
    print(a==b, a~=b) -- true, false
    a={1,2}
    b={1,2}
    print(a==b, a~=b) -- false, true

  .邏輯運算
    and, or, not
    其中,and 和 or 與C語言區(qū)別特別大。
    在這里,請先記住,在Lua中,只有false和nil才計算為false,其它任何數(shù)據(jù)都計算為true,0也是true!
    and 和 or的運算結(jié)果不是true和false,而是和它的兩個操作數(shù)相關(guān)。
    a and b:如果a為false,則返回a;否則返回b
    a or b:如果 a 為true,則返回a;否則返回b

    舉幾個例子:
     print(4 and 5) --> 5
     print(nil and 13) --> nil
     print(false and 13) --> false
     print(4 or 5) --> 4
     print(false or 5) --> 5

    在Lua中這是很有用的特性,也是比較令人混洧的特性。
    我們可以模擬C語言中的語句:x = a? b : c,在Lua中,可以寫成:x = a and b or c。
    最有用的語句是: x = x or v,它相當(dāng)于:if not x then x = v end 。

  .運算符優(yōu)先級,從高到低順序如下:
    ^
    not - (一元運算)
     * /
     + -
     ..(字符串連接)
     < > <= >= ~= ==
     and
     or

==========================================================

 

III. 關(guān)鍵字

  關(guān)鍵字是不能做為變量的。Lua的關(guān)鍵字不多,就以下幾個:
  and break do else elseif
  end false for function if
  in local nil not or
  repeat return then true until while

IV. 變量類型

  怎么確定一個變量是什么類型的呢?大家可以用type()函數(shù)來檢查。Lua支持的類型有以下幾種:

  Nil 空值,所有沒有使用過的變量,都是nil。nil既是值,又是類型。
  Boolean 布爾值
  Number 數(shù)值,在Lua里,數(shù)值相當(dāng)于C語言的double
  String 字符串,如果你愿意的話,字符串是可以包含'\0'字符的
  Table 關(guān)系表類型,這個類型功能比較強大,我們在后面慢慢說。
  Function 函數(shù)類型,不要懷疑,函數(shù)也是一種類型,也就是說,所有的函數(shù),它本身就是一個變量。
  Userdata 嗯,這個類型專門用來和Lua的宿主打交道的。宿主通常是用C和C++來編寫的,在這種情況下,Userdata可以是宿主的任意數(shù)據(jù)類型,常用的有Struct和指針。
  Thread   線程類型,在Lua中沒有真正的線程。Lua中可以將一個函數(shù)分成幾部份運行。如果感興趣的話,可以去看看Lua的文檔。

V. 變量的定義

  所有的語言,都要用到變量。在Lua中,不管你在什么地方使用變量,都不需要聲明,并且所有的這些變量總是全局變量,除非,你在前面加上"local"。
  這一點要特別注意,因為你可能想在函數(shù)里使用局部變量,卻忘了用local來說明。
  至于變量名字,它是大小寫相關(guān)的。也就是說,A和a是兩個不同的變量。
  定義一個變量的方法就是賦值。"="操作就是用來賦值的
  我們一起來定義幾種常用類型的變量吧。
  A. Nil
    正如前面所說的,沒有使用過的變量的值,都是Nil。有時候我們也需要將一個變量清除,這時候,我們可以直接給變量賦以nil值。如:
    var1=nil -- 請注意 nil 一定要小寫

  B. Boolean
    布爾值通常是用在進(jìn)行條件判斷的時候。布爾值有兩種:true 和 false。在Lua中,只有false和nil才被計算為false,而所有任何其它類型的值,都是true。比如0,空串等等,都是true。不要被C語言的習(xí)慣所誤導(dǎo),0在Lua中的的確確是true。你也可以直接給一個變量賦以Boolean類型的值,如:
    varboolean = true

  C. Number
    在Lua中,是沒有整數(shù)類型的,也不需要。一般情況下,只要數(shù)值不是很大(比如不超過100,000,000,000,000),是不會產(chǎn)生舍入誤差的。在很多CPU上,實數(shù)的運算并不比整數(shù)慢。
    實數(shù)的表示方法,同C語言類似,如:
    4 0.4 4.57e-3 0.3e12 5e+20

  D. String
    字符串,總是一種非常常用的高級類型。在Lua中,你可以非常方便的定義很長很長的字符串。
    字符串在Lua中有幾種方法來表示,最通用的方法,是用雙引號或單引號來括起一個字符串的,如:
    "This is a string."
    和C語言相同的,它支持一些轉(zhuǎn)義字符,列表如下:
    \a bell
    \b back space
    \f form feed
    \n newline
    \r carriage return
    \t horizontal tab
    \v vertical tab
    \\ backslash
    \" double quote
    \' single quote
    \[ left square bracket
    \] right square bracket

    由于這種字符串只能寫在一行中,因此,不可避免的要用到轉(zhuǎn)義字符。加入了轉(zhuǎn)義字符的串,看起來實在是不敢恭維,比如:
    "one line\nnext line\n\"in quotes\", 'in quotes'"
    一大堆的"\"符號讓人看起來很倒胃口。如果你與我有同感,那么,我們在Lua中,可以用另一種表示方法:用"[["和"]]"將多行的字符串括起來,如:
    page = [[
    <HTML>
      <HEAD>
        <TITLE>An HTML Page</TITLE>
      </HEAD>
      <BODY>
        <A HREF="http://www.lua.org">Lua</A>
        [[a text between double brackets]]
      </BODY>
    </HTML>
    ]]

    值得注意的是,在這種字符串中,如果含有單獨使用的"[["或"]]"就仍然得用"\["或"\]"來避免歧義。當(dāng)然,這種情況是極少會發(fā)生的。



==================================================================

E. Table
    關(guān)系表類型,這是一個很強大的類型。我們可以把這個類型看作是一個數(shù)組。只是C語言的數(shù)組,只能用正整數(shù)來作索引;在Lua中,你可以用任意類型來作數(shù)組的索引,除了nil。同樣,在C語言中,數(shù)組的內(nèi)容只允許一種類型;在Lua中,你也可以用任意類型的值來作數(shù)組的內(nèi)容,除了nil。
    Table的定義很簡單,它的主要特征是用"{"和"}"來括起一系列數(shù)據(jù)元素的。比如:

    T1 = {} -- 定義一個空表
    T1[1]=10 -- 然后我們就可以象C語言一樣來使用它了。
    T1["John"]={Age=27, Gender="Male"}
    這一句相當(dāng)于:
    T1["John"]={} -- 必須先定義成一個表,還記得未定義的變量是nil類型嗎
    T1["John"]["Age"]=27
    T1["John"]["Gender"]="Male"
    當(dāng)表的索引是字符串的時候,我們可以簡寫成:
    T1.John={}
    T1.John.Age=27
    T1.John.Gender="Male"
    或
    T1.John{Age=27, Gender="Male"}
    這是一個很強的特性。

    在定義表的時候,我們可以把所有的數(shù)據(jù)內(nèi)容一起寫在"{"和"}"之間,這樣子是非常方便,而且很好看。比如,前面的T1的定義,我們可以這么寫:

    T1=
    {
      10, -- 相當(dāng)于 [1] = 10
      [100] = 40,
      John= -- 如果你原意,你還可以寫成:["John"] =
      {
        Age=27, -- 如果你原意,你還可以寫成:["Age"] =27
        Gender=Male -- 如果你原意,你還可以寫成:["Gender"] =Male
      },
      20 -- 相當(dāng)于 [2] = 20
    }

    看起來很漂亮,不是嗎?我們在寫的時候,需要注意三點:
    第一,所有元素之間,總是用逗號","隔開;
    第二,所有索引值都需要用"["和"]"括起來;如果是字符串,還可以去掉引號和中括號;
    第三,如果不寫索引,則索引就會被認(rèn)為是數(shù)字,并按順序自動從1往后編;

    表類型的構(gòu)造是如此的方便,以致于常常被人用來代替配置文件。是的,不用懷疑,它比ini文件要漂亮,并且強大的多。

  F. Function
    函數(shù),在Lua中,函數(shù)的定義也很簡單。典型的定義如下:
    function add(a,b) -- add 是函數(shù)名字,a和b是參數(shù)名字
     return a+b -- return 用來返回函數(shù)的運行結(jié)果
    end

    請注意,return語言一定要寫在end之前。假如你非要在中間放上一句return,那么請寫成:do return end。
    還記得前面說過,函數(shù)也是變量類型嗎?上面的函數(shù)定義,其實相當(dāng)于:
    add = function (a,b) return a+b end
    當(dāng)你重新給add賦值時,它就不再表示這個函數(shù)了。你甚至可以賦給add任意數(shù)據(jù),包括nil (這樣,你就清除了add變量)。Function是不是很象C語言的函數(shù)指針呢?

    和C語言一樣,Lua的函數(shù)可以接受可變參數(shù)個數(shù),它同樣是用"…"來定義的,比如:
    function sum (a,b,…)
    如果想取得…所代表的參數(shù),可以在函數(shù)中訪問arg局部變量(表類型)得到。
    如 sum(1,2,3,4)
    則,在函數(shù)中,a = 1, b = 2, arg = {3, 4}
    更可貴的是,它可以同時返回多個結(jié)果,比如:
    function s()
      return 1,2,3,4
    end
    a,b,c,d = s() -- 此時,a = 1, b = 2, c = 3, d = 4
前面說過,表類型可以擁有任意類型的值,包括函數(shù)!因此,有一個很強大的特性是,擁有函數(shù)的表,哦,我想更恰當(dāng)?shù)膽?yīng)該說是對象吧。Lua可以使用面向?qū)ο缶幊塘恕2恍牛磕俏遗e例如下:

    t =
    {
     Age = 27
     add = function(self, n) self.Age = self.Age+n end
    }
    print(t.Age) -- 27
    t.add(t, 10)
    print(t.Age) -- 37

    不過,t.add(t,10) 這一句實在是有點土對吧?沒關(guān)系,在Lua中,你可以簡寫成:
    t:add(10) -- 相當(dāng)于 t.add(t,10)

  G. Userdata 和 Thread
    這兩個類型的話題,超出了本文的內(nèi)容,就不打算細(xì)說了。

===========================================================

VI. 結(jié)束語

  就這么結(jié)束了嗎?當(dāng)然不是,接下來,需要用Lua解釋器,來幫助你理解和實踐了。這篇小文只是幫助你大體了解Lua的語法。如果你有編程基礎(chǔ),相信會很快對Lua上手了。
  就象C語言一樣,Lua提供了相當(dāng)多的標(biāo)準(zhǔn)函數(shù)來增強語言的功能。使用這些標(biāo)準(zhǔn)函數(shù),你可以很方便的操作各種數(shù)據(jù)類型,并處理輸入輸出。有關(guān)這方面的信息,你可以參考《Programming in Lua 》一書,你可以在網(wǎng)絡(luò)上直接觀看電子版,網(wǎng)址為:http://www.lua.org/pil/index.html
  當(dāng)然,Lua的最強大的功能是能與宿主程序親蜜無間的合作,因此,下一篇文章,我會告訴大家,如何在你的程序中使用Lua語言作為腳本,使你的程序和Lua腳本進(jìn)行交互。

使用流程

1. 函數(shù)的使用

    以下程序演示了如何在Lua中使用函數(shù), 及局部變量
例e02.lua
-- functions 
function pythagorean(a, b) 
local c2 = a^2 + b^2 
return sqrt(c2) 
end 
print(pythagorean(3,4))

運行結(jié)果
5

程序說明
在Lua中函數(shù)的定義格式為:
function 函數(shù)名(參數(shù))
...
end
    與Pascal語言不同, end不需要與begin配對, 只需要在函數(shù)結(jié)束后打個end就可以了.本例函數(shù)的作用是已知直角三角形直角邊, 求斜邊長度. 參數(shù)a,b分別表示直角邊長,
    在函數(shù)內(nèi)定義了local形變量用于存儲斜邊的平方. 與C語言相同, 定義在函數(shù)內(nèi)的代碼不會被直接執(zhí)行, 只有主程序調(diào)用時才會被執(zhí)行.
    local表示定義一個局部變量, 如果不加local剛表示c2為一個全局變量, local的作用域是在最里層的end和其配對的關(guān)鍵字之間, 如if ... end, while ... end等。全局變量的作用域是整個程序。

2. 循環(huán)語句

例e03.lua
-- Loops 
for i=1,5 do 
print("i is now " .. i) 
end

運行結(jié)果
i is now 1 
i is now 2 
i is now 3 
i is now 4 
i is now 5

程序說明
    這里偶們用到了for語句
for 變量 = 參數(shù)1, 參數(shù)2, 參數(shù)3 do
循環(huán)體
end
    變量將以參數(shù)3為步長, 由參數(shù)1變化到參數(shù)2
例如: 
for i=1,f(x) do print(i) end
for i=10,1,-1 do print(i) end

    這里print("i is now " .. i)中,偶們用到了..,這是用來連接兩個字符串的,偶在(1)的試試看中提到的,不知道你們答對了沒有。雖然這里i是一個整型量,Lua在處理的時候會自動轉(zhuǎn)成字符串型,不需偶們費心。

3. 條件分支語句

例e04.lua
-- Loops and conditionals 
for i=1,5 do
print(“i is now “ .. i)
if i < 2 then 
print(“small”) 
elseif i < 4 then 
print(“medium”) 
else 
print(“big”) 
end 
end

運行結(jié)果
i is now 1 
small 
i is now 2 
medium 
i is now 3 
medium 
i is now 4 
big 
i is now 5 
big

程序說明
    if else用法比較簡單, 類似于C語言, 不過此處需要注意的是整個if只需要一個end,哪怕用了多個elseif, 也是一個end.
例如
if op == "+" then
r = a + b
elseif op == "-" then
r = a - b
elseif op == "*" then
r = a*b
elseif op == "/" then
r = a/b
else
error("invalid operation")
end


4.試試看

    Lua中除了for循環(huán)以外, 還支持多種循環(huán), 請用while...do和repeat...until改寫本文中的for程序。

數(shù)組的使用

1.簡介

    Lua語言只有一種基本數(shù)據(jù)結(jié)構(gòu), 那就是table, 所有其他數(shù)據(jù)結(jié)構(gòu)如數(shù)組啦,類啦, 都可以由table實現(xiàn).

2.table的下標(biāo)

例e05.lua
-- Arrays 
myData = {} 
myData[0] = “foo” 
myData[1] = 42

-- Hash tables 
myData[“bar”] = “baz”

-- Iterate through the 
-- structure 
for key, value in myData do 
print(key .. “=“ .. value) 
end

輸出結(jié)果
0=foo 
1=42 
bar=baz

程序說明
    首先定義了一個table myData={}, 然后用數(shù)字作為下標(biāo)賦了兩個值給它. 這種定義方法類似于C中的數(shù)組, 但與數(shù)組不同的是, 每個數(shù)組元素不需要為相同類型,就像本例中一個為整型, 一個為字符串.

    程序第二部分, 以字符串做為下標(biāo), 又向table內(nèi)增加了一個元素. 這種table非常像STL里面的map. table下標(biāo)可以為Lua所支持的任意基本類型, 除了nil值以外.

    Lua對Table占用內(nèi)存的處理是自動的, 如下面這段代碼
a = {}
a["x"] = 10
b = a -- `b' refers to the same table as `a'
print(b["x"]) --> 10
b["x"] = 20
print(a["x"]) --> 20
a = nil -- now only `b' still refers to the table
b = nil -- now there are no references left to the table
    b和a都指向相同的table, 只占用一塊內(nèi)存, 當(dāng)執(zhí)行到a = nil時, b仍然指向table,
    而當(dāng)執(zhí)行到b=nil時, 因為沒有指向table的變量了, 所以Lua會自動釋放table所占內(nèi)存

3.Table的嵌套

    Table的使用還可以嵌套,如下例
例e06.lua
-- Table ‘constructor’ 
myPolygon = { 
color=“blue”, 
thickness=2, 
npoints=4; 
{x=0, y=0}, 
{x=-10, y=0}, 
{x=-5, y=4}, 
{x=0, y=4} 
}

-- Print the color 
print(myPolygon[“color”])

-- Print it again using dot 
-- notation 
print(myPolygon.color)

-- The points are accessible 
-- in myPolygon[1] to myPolygon[4]

-- Print the second point’s x 
-- coordinate 
print(myPolygon[2].x)

程序說明

    首先建立一個table, 與上一例不同的是,在table的constructor里面有{x=0,y=0}, 這是什么意思呢? 這其實就是一個小table, 定義在了大table之內(nèi), 小table的table名省略了.最后一行myPolygon[2].x,就是大table里面小table的訪問方式.

posted @ 2012-11-29 16:32 RTY 閱讀(401) | 評論 (0)編輯 收藏

xcode4的環(huán)境變量,Build Settings參數(shù),workspace及聯(lián)編設(shè)置

一、xcode4中的環(huán)境變量

$(BUILT_PRODUCTS_DIR)

build成功后的,最終產(chǎn)品路徑--可以在Build Settings參數(shù)的Per-configuration Build Products Path項里設(shè)置

$(TARGET_NAME)

目標(biāo)工程名稱

$(SRCROOT)

工程文件(比如Nuno.xcodeproj)的路徑 

$(CURRENT_PROJECT_VERSION)

當(dāng)前工程版本號

 

其他:

當(dāng)編譯靜態(tài)庫,設(shè)備選模擬器(iPhone 5.0 Simulator),未設(shè)置任何Build Settings參數(shù)時,默認(rèn)的基礎(chǔ)路徑:

/Users/xxx/Library/Developer/Xcode/DerivedData/xxxWorkspace-caepeadwrerdcrftijaolkkagbjf

下面用$()代替上面一長串東東

$(SYMROOT) = $()/Build/Products

$(BUILD_DIR) = $()/Build/Products

$(BUILD_ROOT) =  $()/Build/Products

這三個變量中的$()不會隨著Build Settings參數(shù)的設(shè)置而改變

相反,以下可以通過設(shè)置而改變

$(CONFIGURATION_BUILD_DIR) = $()/Build/Products/Debug-iphonesimulator

$(BUILT_PRODUCTS_DIR) = $()/Build/Products/Debug-iphonesimulator

$(CONFIGURATION_TEMP_DIR) = $()/Build/Intermediates/UtilLib.build/Debug-iphonesimulator

$(TARGET_BUILD_DIR) = $()/Build/Products/Debug-iphonesimulator

$(SDK_NAME) = iphonesimulator5.0

$(PLATFORM_NAME) = iphonesimulator

$(CONFIGURATION) = Debug

$(TARGET_NAME) = UtilLib

$(EXECUTABLE_NAME) = libUtilLib.a 可執(zhí)行文件名

${IPHONEOS_DEPLOYMENT_TARGET} 5.0

$(ACTION) = build

$(CURRENTCONFIG_SIMULATOR_DIR) 當(dāng)前模擬器路徑 

$(CURRENTCONFIG_DEVICE_DIR) 當(dāng)前設(shè)備路徑 

 

$(BUILD_DIR)/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME =

$()/Build/Products/Debug-iphonesimulator

$(PROJECT_TEMP_DIR)/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME) = $()/Build/Intermediates/UtilLib.build/Debug-iphonesimulator

 

自定義變量

${CONFIGURATION}-iphoneos 表示:Debug-iphoneos

${CONFIGURATION}-iphonesimulator 表示:Debug-iphonesimulator

$(CURRENTCONFIG_DEVICE_DIR) = ${SYMROOT}/${CONFIGURATION}-iphoneos

$(CURRENTCONFIG_SIMULATOR_DIR) = ${SYMROOT}/${CONFIGURATION}-iphonesimulator

自定義一個設(shè)備無關(guān)的路徑(用來存放各種架構(gòu)arm6/arm7/i386輸出的產(chǎn)品)

$(CREATING_UNIVERSAL_DIR) = ${SYMROOT}/${CONFIGURATION}-universal

自定義變量代表的值

$(CURRENTCONFIG_DEVICE_DIR) = $()/Build/Products/Debug-iphoneos

$(CURRENTCONFIG_SIMULATOR_DIR) = $()/Build/Products/Debug-iphonesimulator

$(CREATING_UNIVERSAL_DIR) = $()/Build/Products/Debug-universal

 

iphoneos5.0下的編譯腳本:

xcodebuild -project "UtilLib.xcodeproj" -configuration "Debug" -target "UtilLib" -sdk "iphoneos5.0" -arch "armv6 armv7" build RUN_CLANG_STATIC_ANALYZER=NO  $(BUILD_DIR)="${BUILD_DIR}" BUILD_ROOT="${BUILD_ROOT}"

 

iphonesimulator5.0下的編譯腳本:

xcodebuild -project "UtilLib.xcodeproj" -configuration "Debug" -target "UtilLib" -sdk "iphonesimulator5.0" -arch "i386" build RUN_CLANG_STATIC_ANALYZER=NO $(BUILD_DIR)="${BUILD_DIR}"  BUILD_ROOT="${BUILD_ROOT}"

加上下面一句表示輸出到文件:

> "${BUILD_ROOT}.build_output"

 

lipo腳本工具:合并iPhone模擬器和真機的靜態(tài)類庫,生成通用庫

lipo -create -output "${CREATING_UNIVERSAL_DIR}/${EXECUTABLE_NAME}" "${CURRENTCONFIG_DEVICE_DIR}/${EXECUTABLE_NAME}"         "${CURRENTCONFIG_SIMULATOR_DIR}/${EXECUTABLE_NAME}"

意思是:把"${CURRENTCONFIG_DEVICE_DIR}目錄下的.a文件,和${CURRENTCONFIG_SIMULATOR_DIR}目錄下的.a文件合并,

在${CREATING_UNIVERSAL_DIR}目錄下,生成兩個設(shè)備都通用的靜態(tài)庫,

例如:lipo -create -output xy.a x.a y.a

 

二、xcode4中build Settings常見參數(shù)解析

1.Installation Directory:安裝路徑

靜態(tài)庫編譯時,在Build Settings中Installation Directory設(shè)置“$(BUILT_PRODUCTS_DIR)”

Skip Install設(shè)為YES

Installation Directory默認(rèn)為/usr/local/lib

因為Build Location默認(rèn)時,.a文件會放在很長(比如:/Users/xxx/Library/Developer/Xcode/DerivedData/xxxProgram

dalrvzehhtesxdfqhxixzafvddwe/Build/Products/Debug-iPhoneos)的路徑下,或是我們target指定的路徑

Skip Install如果是NO,可能會被安裝到默認(rèn)路徑/usr/local/lib

2.Public Headers Folder Path:對外公開頭文件路徑

設(shè)為“include”(具體的頭文件路徑為:$(BUILT_PRODUCTS_DIR)/include/xx.h)

在最終文件.a同級目錄下生成一個include目錄

默認(rèn):/usr/local/include

Public Headers Folder Path這個路徑就是使用這lib的某工程需要依賴的外部頭文件.導(dǎo)入這路徑后,#include/import "xx.h"才能看到

3.User Header Search Paths:依賴的外部頭文件搜索路徑

設(shè)置為“$(BUILT_PRODUCTS_DIR)/include”

和2中路徑對應(yīng)

4.Per-configuration Build Products Path:最終文件路徑

比如設(shè)為“../app”,就會在工程文件.xcodeproj上一層目錄下的app目錄里,創(chuàng)建最終文件

默認(rèn)為$(BUILD_DIR)/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME) 

等于$(BUILT_PRODUCTS_DIR)

5.Per-configuration Intermediate Build Files Path:臨時中間文件路徑

默認(rèn)為:$(PROJECT_TEMP_DIR)/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)

6.Code Signing Identity:真機調(diào)試的證書選擇

選一個和Bundle identifier相對應(yīng)的證書

Library Search Paths:庫搜索路徑

Architectures:架構(gòu),設(shè)為 armv6 或 armv7

Valid Architectures:應(yīng)用框架,可以設(shè)為 armv6、 armv7 或i386

Product Name:工程文件名,默認(rèn)為$(TARGET_NAME)

Info.plist File:info文件路徑

Build Variants:默認(rèn)為normal

Other Linker Flags:其他鏈接標(biāo)簽

設(shè)為“-ObjC”

當(dāng)導(dǎo)入的靜態(tài)庫使用了類別,需要設(shè)為-ObjC

iOS Deployment Target:ios部署對象

比如可以選擇設(shè)為,ios3到ios5的一種版本

Prefix Header:預(yù)編頭文件(比如:UtilLib/UtilLib-Prefix.pch)

Precompile Prefix Header:設(shè)為“Yes”,表示允許加入預(yù)編譯頭

 

三、workspace(工作區(qū))

作用:管理多個工程(project),多工程聯(lián)編

 

四、workspace多工程聯(lián)編設(shè)置

一、

1.新建一個靜態(tài)庫工程,比如UtilLib,并生成UtilLib.h和UtilLib.m文件

2.選中需要公開的頭文件,

把右側(cè)欄的Target Membership中設(shè)置為public

或則,選中工程目錄target的Build Phases標(biāo)簽的copy headers項,在public中添加要公開的頭文件

3.Architectures設(shè)為:armv6 armv7

4.Valid Architectures設(shè)為:armv6 armv7 i386

5.Build Products Path設(shè)為:$(SRCROOT)/../build

6.Per-configuration Build Products Path設(shè)為:

$(SRCROOT)/../build/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)

7.Per-configuration Intermediate Build Files Path設(shè)為:

$(SRCROOT)/../build/$(TARGET_NAME).build/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)

8.設(shè)置安裝路徑:Installation Directory項

9.設(shè)置對外公開的頭文件路徑:Public Headers Folder Path項


10.為靜態(tài)庫添加依賴的shell腳本

選中工程目錄target的Build Phases標(biāo)簽,點擊由下角的Add Build Phase按鈕

在彈出的菜單里選擇Add run script項,然后頁面中會多出一個Run Script項

在黑框里填寫"$SRCROOT/mergeArmSymbols.sh"

建立對此腳本的依賴(編譯靜態(tài)庫的后會運行此腳本)

如果編譯時設(shè)備選的是iphone simulator:

則此腳本會在對應(yīng)iphone device的產(chǎn)品目錄Debug-iphoneos中,生成對device有用的.a靜態(tài)庫,

相反,如果設(shè)備選的是iphone device:

則此腳本會在對應(yīng)iphone simulator的產(chǎn)品目錄Debug-iphoneos中,生成對simulator有用的.a靜態(tài)庫

最后,此腳本調(diào)用lipo工具,把本工程生成靜態(tài)庫與此腳本生成的靜態(tài)庫合并,生成simulator和device都通用的.a文件

 

11.具體bash shell腳本如下

mergeArmSymbols.sh

下載右邊的圖片,然后把后綴改為.sh(其實就是上面的腳本,因為博客園只能上傳圖片)

靜態(tài)庫編譯后的目錄結(jié)構(gòu)如下:

 

二、 

1.新建主工程,比如Nuno,添加對靜態(tài)庫的依賴

點擊工程,在Build Phases標(biāo)簽的Link Binary With Libraries項中點擊加號添加UtilLib.a庫

選中上面的紅色項,在右邊欄的Location選Relative to Project,把值設(shè)為../libs/libUtilLib.a

2.設(shè)置主工程依賴的外部頭文件路徑:User Header Search Paths項

$(SRCROOT)/../include

3.設(shè)置Header Search Paths為:$(SRCROOT)/../include

4.設(shè)置Library Search Paths為:$(SRCROOT)/../libs

編譯運行即可實現(xiàn)聯(lián)編 

 

(備注:選擇模擬器iphone 5.0 simulator,編譯靜態(tài)庫的時,最終文件會在Debug-iphonesimulator,就算成功.a文件還是紅色,

這是可能是xcode的bug,不會自動切換路徑

因為$(BUILT_PRODUCTS_DIR)所指的位置,是build/Debug-iphonesos,不是包含最終.a文件的Debug-iphonesimulator;

選擇ios Device,編譯成的最終文件才在build/Debug-iphonesos下,.a文件變成非紅色

所有得用mergeArmSymbols.sh腳本來解決)


posted @ 2012-11-28 16:51 RTY 閱讀(679) | 評論 (0)編輯 收藏

1.    // TODO —— 表示尚未完成的待辦事項。
2.    // XXX —— 表示被注釋的代碼雖然實現(xiàn)了功能,但是實現(xiàn)方案有待商榷,希望將來能改進(jìn)。
3.    // FIXME —— 表示被注釋的代碼需要被修正。

posted @ 2012-11-28 12:21 RTY 閱讀(440) | 評論 (0)編輯 收藏

UIBarButtonSystemItem的樣式圖片

 

typedef enum {
    UIBarButtonSystemItemDone,
    UIBarButtonSystemItemCancel,
    UIBarButtonSystemItemEdit,  
    UIBarButtonSystemItemSave,  
    UIBarButtonSystemItemAdd,
    UIBarButtonSystemItemFlexibleSpace,
    UIBarButtonSystemItemFixedSpace,
    UIBarButtonSystemItemCompose,
    UIBarButtonSystemItemReply,
    UIBarButtonSystemItemAction,
    UIBarButtonSystemItemOrganize,
    UIBarButtonSystemItemBookmarks,
    UIBarButtonSystemItemSearch,
    UIBarButtonSystemItemRefresh,
    UIBarButtonSystemItemStop,
    UIBarButtonSystemItemCamera,
    UIBarButtonSystemItemTrash,
    UIBarButtonSystemItemPlay,
    UIBarButtonSystemItemPause,
    UIBarButtonSystemItemRewind,
    UIBarButtonSystemItemFastForward,
#if __IPHONE_3_0 <= __IPHONE_OS_VERSION_MAX_ALLOWED
    UIBarButtonSystemItemUndo,
    UIBarButtonSystemItemRedo,
#endif
#if __IPHONE_4_0 <= __IPHONE_OS_VERSION_MAX_ALLOWED
    UIBarButtonSystemItemPageCurl,
#endif
} UIBarButtonSystemItem;

 

 

圖片如下:

UIBarButtonSystemItemAdd

UIBarButtonSystemItemCompose

UIBarButtonSystemItemReply

UIBarButtonSystemItemAction

UIBarButtonSystemItemOrganize

UIBarButtonSystemItemBookmarks

UIBarButtonSystemItemSearch

UIBarButtonSystemItemRefresh

UIBarButtonSystemItemStop

UIBarButtonSystemItemCamera

UIBarButtonSystemItemTrash

UIBarButtonSystemItemPlay

UIBarButtonSystemItemPause

UIBarButtonSystemItemRewind

UIBarButtonSystemItemFastForward

UIBarButtonSystemItemUndo

UIBarButtonSystemItemRedo

天下風(fēng)云出我輩, 一入江湖歲月催. 皇圖霸業(yè)笑談中, 不勝人生一場醉.

posted @ 2012-11-26 14:16 RTY 閱讀(3615) | 評論 (0)編輯 收藏

原文:http://blog.csdn.net/weiqubo/article/details/8152326

由init、loadView、viewDidLoad、viewDidUnload、dealloc的關(guān)系說起

分類: iOS 273人閱讀 評論(0) 收藏 舉報

對于iphone開發(fā)人員來說,內(nèi)存管理是極為重要的技巧,哪怕程序的功能再強大,設(shè)計再漂亮,如果內(nèi)存控制不好,也難逃程序莫名退出的噩運,這與網(wǎng)頁開發(fā)是完全不同的。

內(nèi)存控制里面有很多門道,在這里分析一下 viewDidUnload 和 dealloc 的區(qū)別,關(guān)于這兩者的區(qū)別的文章很多,但是大都是摘抄和翻譯官方文檔,有的也只是簡單的說兩句,并沒有詳細(xì)說出兩者具體的區(qū)別。

在了解兩者之間的區(qū)別,首先要知道 view 的生命周期,google 里面有很多文章,可以先去搜一下,這里就不詳解了。

顧名思義  viewDidUnload 就是當(dāng) view 被卸載以后執(zhí)行的語句,它與 viewDidLoad 是相互呼應(yīng)的。大家都知道官方的解釋是執(zhí)行類似

 

self.myOutlet = nil;

 

的命令,但是為什么這么干,什么時候調(diào)用這個方法呢?

這個方法是不能手動調(diào)用的,它實際上是當(dāng)應(yīng)用程序接收到手機內(nèi)存警告的時候自動調(diào)用的方法,目的就是清空內(nèi)存除當(dāng)前 viewController 以外所有已經(jīng)加載過的 viewController 里面的暫時不再使用的一些控件或數(shù)據(jù),以避免應(yīng)用程序應(yīng)消耗內(nèi)存過多被強制關(guān)閉。記住,是除當(dāng)前正在展示的 view 所屬 viewController 以外所有已經(jīng)在內(nèi)存里面的 viewController 執(zhí)行 viewDidUnload 方法, 而不是當(dāng)前 viewController 執(zhí)行 viewDidUnload,當(dāng)然,這些 viewController 不會被 dealloc。所以在 viewDidUnload 里面一般都是釋放 IBOutlet 變量和在 viewDidLoad、viewWillAppear、viewDidAppear 等方法能夠重建的數(shù)據(jù)。而由其他頁面?zhèn)鬟f過來的數(shù)據(jù)或者無法經(jīng)過 viewDidLoad、viewWillAppear、viewDidAppear 等方法重建的數(shù)據(jù)則不能釋放,舉例子說如果在 navigationController 由上一個頁面?zhèn)鬟f過來的一張圖片,在 viewDidUnload 里被釋放的話,則當(dāng) view 再次加載的時候就無法恢復(fù)了。

那為什么要寫成 self.myOutlet = nil; ,實際上這個語法是執(zhí)行了 property 里的setter 方法,而不是一個簡單的變量賦值,它干了兩件事:1、老數(shù)據(jù) release 掉,2、新數(shù)據(jù)(nil)retain(當(dāng) property 設(shè)置為 retain 的情況下),當(dāng)然對 nil retain 是無意義的。如果寫成 myOutlet = nil,那就是簡單的把 myOutlet 指向 nil,這樣內(nèi)存就泄漏了,因為老數(shù)據(jù)沒有 release。而如果僅僅寫成 [myOutlet release] 也會有問題,因為當(dāng) view 被 dealloc 的時候會 再次 release,程序就出錯了,而對 nil release 是沒有問題的。
 
dealloc 是當(dāng)前 viewController 被釋放的時候,清空所有當(dāng)前 viewController 里面的實體和數(shù)據(jù)來釋放內(nèi)存,該方法也是自動調(diào)用的,無需手動執(zhí)行。舉例說明當(dāng) modalView 被 dismissModalViewControllerAnimated 或者 navigationController 回到上一頁的時候,這個方法就會被自動調(diào)用。因為這個頁面已經(jīng)不再使用了,所以可以把所有實體和數(shù)據(jù)都釋放(release)掉。

其實兩者最大的區(qū)別就是: viewDidUnload 是內(nèi)存除當(dāng)前以外所有 viewController 同時執(zhí)行,而 dealloc 只是當(dāng)前 viewController 執(zhí)行。這個是網(wǎng)上的材料沒有說明的。

個人拙見,不對之處還請?zhí)嵴?br />
PS: 很多朋友都說無法調(diào)試 viewDidUnload,其實是可以的。方法是在 iOS 模擬器的菜單里選 硬件->模擬內(nèi)存警告,這個時候就可以看到 viewDidUnload 里面 NSLog 的東西了,可以試試在打開過的 viewController 里都 NSLog 一下看看效果。而 dealloc 里面可以直接 NSLog。



由init、loadView、viewDidLoad、viewDidUnload、dealloc的關(guān)系說起

init方法

在init方法中實例化必要的對象(遵從LazyLoad思想)

init方法中初始化ViewController本身

 loadView方法

當(dāng)view需要被展示而它卻是nil時,viewController會調(diào)用該方法。不要直接調(diào)用該方法。

如果手工維護(hù)views,必須重載重寫該方法

如果使用IB維護(hù)views,必須不能重載重寫該方法

loadView和IB構(gòu)建view

你在控制器中實現(xiàn)了loadView方法,那么你可能會在應(yīng)用運行的某個時候被內(nèi)存管理控制調(diào)用。 如果設(shè)備內(nèi)存不足的時候, view 控制器會收到didReceiveMemoryWarning的消息。 默認(rèn)的實現(xiàn)是檢查當(dāng)前控制器的view是否在使用。 如果它的view不在當(dāng)前正在使用的view hierarchy里面,且你的控制器實現(xiàn)了loadView方法,那么這個view將被release, loadView方法將被再次調(diào)用來創(chuàng)建一個新的view。

 

viewDidLoad方法

viewDidLoad 此方法只有當(dāng)view從nib文件初始化的時候才被調(diào)用。

重載重寫該方法以進(jìn)一步定制view

在iPhone OS 3.0及之后的版本中,還應(yīng)該重載重寫viewDidUnload來釋放對view的任何索引

viewDidLoad后調(diào)用數(shù)據(jù)Model

viewDidUnload方法

當(dāng)系統(tǒng)內(nèi)存吃緊的時候會調(diào)用該方法(注:viewController沒有被dealloc)

內(nèi)存吃緊時,在iPhone OS 3.0之前didReceiveMemoryWarning是釋放無用內(nèi)存的唯一方式,但是OS 3.0及以后viewDidUnload方法是更好的方式

在該方法中將所有IBOutlet(無論是property還是實例變量)置為nil(系統(tǒng)release view時已經(jīng)將其release掉了)

在該方法中釋放其他與view有關(guān)的對象、其他在運行時創(chuàng)建(但非系統(tǒng)必須)的對象、在viewDidLoad中被創(chuàng)建的對象、緩存數(shù)據(jù)等 release對象后,將對象置為nil(IBOutlet只需要將其置為nil,系統(tǒng)release view時已經(jīng)將其release掉了)

一般認(rèn)為viewDidUnload是viewDidLoad的鏡像,因為當(dāng)view被重新請求時,viewDidLoad還會重新被執(zhí)行

viewDidUnload中被release的對象必須是很容易被重新創(chuàng)建的對象(比如在viewDidLoad或其他方法中創(chuàng)建的對象),不要release用戶數(shù)據(jù)或其他很難被重新創(chuàng)建的對象

dealloc方法

viewDidUnload和dealloc方法沒有關(guān)聯(lián),dealloc還是繼續(xù)做它該做的事情

看到以下的代碼

- (void)viewDidUnload {

self.detailViewController = nil; 

self.languageNames = nil; 

self.languageCodes = nil;

}

- (void)dealloc {

[detailViewController release];

 [languageNames release]; 

[languageCodes release]; 

[super dealloc];

}


如果是先調(diào)用viewDidUnload后再調(diào)用dealloc, 那么languageNames都已經(jīng)是nil了,再掉release有什么意義呢?
原 因似乎是, 對一個viewcontroller來說,它的數(shù)據(jù)的初始化在init中,而它管理的view采用了lazy load的方式,也就是有需要的時候才會載入, 所以跟view相關(guān)的數(shù)據(jù)可以在viewDidLoad(也就是在view被載入的時候)進(jìn)行初始化。當(dāng)內(nèi)存緊張的時候, ios會銷毀點一些view, 通過調(diào)用viewDidUnload (里面一般也只是把跟view相關(guān)的數(shù)據(jù)設(shè)為nil), 但這個時候viewcontroller本身還在, 所以它的dealloc不會被調(diào)用,除非是到了viewcontroller也被銷毀的時候

posted @ 2012-11-23 10:41 RTY 閱讀(512) | 評論 (0)編輯 收藏

隔上一次寫iPad app開發(fā)文章已經(jīng)是10個月,那篇iPad app開發(fā)概述還不錯,曾經(jīng)成為了google關(guān)鍵字“iPad app 開發(fā)”搜索的第一位,可能是大牛們都太忙于賺app store的錢了,留下我這個小蝦來寫文章。這次的文章集中與iOS的多核編程和內(nèi)存管理,為什么?因為iPad 2已經(jīng)是雙核CPU了!雖然iPad 1的應(yīng)用已經(jīng)不慢了,但大家完全可以使用蘋果的多核編程框架來寫出更加responsive的應(yīng)用。

 

多核運算

在iOS中concurrency編程的框架就是GCD(Grand Central Dispatch), GCD的使用非常簡單。它把任務(wù)分派到不同的queue隊列來處理。開發(fā)者把任務(wù)代碼裝到一個個block里面,操作系統(tǒng)把這些任務(wù)代碼分派到不同的資源里去處理,一個簡單的例子來說,為什么初學(xué)者寫tableview的時候,滑動列表時總會很卡,因為很多初學(xué)者把圖片裝載放到main thread主線程去執(zhí)行,例如我們要滑動暢順的話,iOS最快可以1秒內(nèi)刷新60次,如何你的一個cell的文字和圖片裝載超過1/60秒的話,自然就會卡。所以一般我們會把圖片裝載這些需要多點時間的移出main thread來處理,對于用GCD來說,就是把圖片載入放到另外一個queue隊列中來異步執(zhí)行,當(dāng)資源準(zhǔn)備好了后,放回到main thread中顯示出來。main thread在GCD中就是main queue。

 

創(chuàng)建一個新queue隊列的代碼:

 

 

C代碼  收藏代碼
  1. dispatch_queue_t network_queue;  
  2.   
  3. network_queue = dispatch_queue_create("com.myapp.network", nill);  

 

例如,我們圖片讀取放到network_queue來進(jìn)行異步執(zhí)行

 

 

C代碼  收藏代碼
  1. dispatch_async(network_queue, ^{    
  2.     UIImage *cellImage = [self loadMyImageFromNetwork:image_url];    
  3.     // 將圖片cache到本地    
  4.     [self cacheImage:cellImage];    
  5.     
  6.     .....    
  7.         
  8. } );  
 

 

dispatch_async的意思就是將任務(wù)進(jìn)行異步并行處理,不一定需要一個任務(wù)處理完后才能處理下一個。以上代碼loadMyImageFromNetwork的意思就是從網(wǎng)絡(luò)中讀取圖片,這個任務(wù)交給network_queue來處理。這樣讀取圖片的時間過長也不會阻塞主線程界面的處理。

 

當(dāng)我們處理完圖片后,應(yīng)該更新界面,從queue的概念去設(shè)計,就是要將更新界面的代碼放到main queue中去,因為iOS里面永遠(yuǎn)是主線程來刷新重畫UI。所以代碼應(yīng)該為,

 

 

C代碼  收藏代碼
  1. dispatch_async(network_queue, ^{    
  2.     UIImage *cellImage = [self loadMyImageFromNetwork:image_url];    
  3.     // 將圖片cache到本地    
  4.     [self cacheImage:cellImage];    
  5.     
  6.    // 回到主線程    
  7.    dispatch_async(dispatch_get_main_queue(), ^{    
  8.       // 顯示圖片到界面    
  9.       [self displayImageToTableView:cellImage];    
  10.    }];    
  11.         
  12. } );  
 

 

dispatch_get_main_queue() 函數(shù)就是返回主線程,^{} 封裝的就是任務(wù)代碼,這樣嵌套方式就可以從一個隊列queue,跳到另一個queue,就是這么簡單。

 

我們一般可以把networking有關(guān)的代碼放到一個queue,把圖片resize的代碼放到另外一個queue,處理完后更新界面,只需要嵌套跳回到 main queue。這樣加上幾行代碼,你的程序就可以利用到系統(tǒng)多核資源,把具體的調(diào)度工作交給了操作系統(tǒng)自己來分配。有了這樣的代碼,不管你的硬件是單核,雙核還是iMac的4核,甚至8核,都可以非常好地并行處理。

 

 

內(nèi)存管理

我一直驚嘆iOS和Objective-C內(nèi)存處理能力,例如iPad版本的iWork,Pages應(yīng)用就是一個內(nèi)存處理技術(shù)應(yīng)用的鬼斧神工之作。想想256M內(nèi)存的iPad,可以帶來如此的華麗的界面同時獲得如此流暢的用戶體驗,真是不簡單。原因就是iOS一直提倡開發(fā)者在有限硬件資源內(nèi)寫出最優(yōu)化的代碼,使用CPU最少,占用內(nèi)存最小。

 

(以下代碼適用于iOS SDK 4.1, 由于新SDK 4.2對內(nèi)存使用有新改動,所以可能有不同。。。)

1. 盡量少的UIView層

通常我們喜歡把很多控件層(UILabel,UIButton,UIView等)一起放到一個大的UIView容器來顯示我們的內(nèi)容,這個方法一般是可以的,但是如果要經(jīng)常重新刷新內(nèi)容的大區(qū)域界面,多數(shù)發(fā)生在iPad的應(yīng)用中,這個方法會帶來過多的內(nèi)存使用和動畫的延遲(比較卡),例如,scrollview的動畫比較卡,又或者,經(jīng)常收到內(nèi)存警告。其中一個重要原因是每個控件,特別是透明底的,會多次重新繪制(drawRect)過多。其解決辦法是,盡量將幾個控件合并到一個層上來顯示,這樣系統(tǒng)會減少系統(tǒng)調(diào)用drawRect,從而帶來性能上的提升。

 

很簡單的一個例子,就是iNotes提供手寫功能,用戶可以在iPad屏幕上寫出不同的筆畫,開始的設(shè)計是,用戶每寫一劃,iNotes就會生成一個新的透明底UIView來保持這個筆畫,用戶寫了10筆,系統(tǒng)就生產(chǎn)了10個UIView,每個view的大小都是整個屏幕的,以便用戶的undo操作。這個方案帶來嚴(yán)重的內(nèi)存問題,因為系統(tǒng)將每個層都保持一個bitmap圖,一個像素需要4bit來算,一個層的大小就是 4x1024x768 ~ 3M, 10個層就是 10x3M = 30M,很明顯,iPad很快爆出內(nèi)存警告。

 

這個例子最后的方案是,所有筆畫都畫在同一個層,iNotes可以保存筆畫的點進(jìn)行undo操作。這樣的方案就是無論用戶畫多少筆畫,界面重畫需要的資源都是一樣的。

 

2. 顯示最佳尺寸的圖片

很多程序員比較懶,網(wǎng)絡(luò)上拿下來的圖片,直接就用UIImageView將其顯示給用戶,這樣的后果就是,程序需要一直保存著大尺寸的圖片到內(nèi)存。解決辦法應(yīng)該是先將圖片縮小到需要顯示的尺寸,釋放大尺寸圖片的內(nèi)存,然后再顯示到界面給用戶。

 

3. 盡量使用圖片pattern,而不是一張大的圖片

例如,很多界面設(shè)計者喜歡在界面上放一個大底圖,但這個底圖是老是占用著內(nèi)存的,最佳方案是,設(shè)計出一個小的pattern圖,然后用這個方案顯示成底圖。

 

C代碼  收藏代碼
  1. UIImage *smallImage = [[UIImage alloc] initWithContentsOfFile:path];  
  2.   
  3. backgroundView.backgroundColor = [UIColor colorWithPatternImage:smallImage];  
  4.   
  5. [smallImage release];  
 

 

4. 使用完資源后,立即釋放

一般objective-c的習(xí)慣是,用完的資源要立即釋放,因為明白什么時候用完某個資源的是程序員你自己。

例如,我們要讀較大的圖片,把它縮小后,顯示到界面去。當(dāng)大圖片使用完成后,應(yīng)該立即釋放。代碼如下:

 

C代碼  收藏代碼
  1. UIImage *fullscreenImage = [[UIImage alloc] initWithContentOfFile:path];  
  2. UIImage *smallImage = [self resizeImage:fullscreenImage];  
  3.   
  4. [fullscreenImage release];  
  5.   
  6. imageView.image = smallImage;  
  7.   
  8. ......  
 

5. 循環(huán)中大量生成的自動釋放autorelease對象,可以考慮使用autorelease pool封裝

代碼范例:

C代碼  收藏代碼
  1. for(UIView *subview in bigView.subviews) {  
  2.     // 使用autorelease pool自動釋放對象池  
  3.     NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];  
  4.   
  5.     UIImageView *imageView = (UIImageView *)subview;  
  6.       
  7.     // subview處理代碼  
  8.     .......  
  9.   
  10.     // 銷毀自動釋放對象  
  11.     [pool  drain];  
  12. }  

 自動釋放對象池把每個循環(huán)內(nèi)生成的臨時對象使用完后立即釋放

 

以上的意見是本人多年來編寫iPad/iPhone程序的經(jīng)驗,另外iOS4.0的multi-tasking特性發(fā)布后,程序可以被調(diào)入后臺運行,蘋果工程師的意見是,進(jìn)入后臺運行時,你的應(yīng)用應(yīng)該釋放掉能釋放的對象,盡量保持在16M左右,這樣別的程序運行時才不容易把你的應(yīng)用擠掉。

 

--------------------------------------------------

太久沒有寫東西了,中文寫作能力退步了,大家別見怪,多給給意見

posted @ 2012-11-16 06:46 RTY 閱讀(330) | 評論 (0)編輯 收藏

一般發(fā)生在使用最新的XCode。@import url(http://m.shnenglu.com/cutesoft_client/cuteeditor/Load.ashx?type=style&file=SyntaxHighlighter.css);@import url(/css/cuteeditor.css);

怎么來解決問題呢,其實

直接一點,就是在指定Complier的時候,選擇Clang,不要選擇GCC!

你可以試試!有問題可以咨詢我!

posted @ 2012-11-07 06:22 RTY 閱讀(1252) | 評論 (0)編輯 收藏

僅列出標(biāo)題
共31頁: 1 2 3 4 5 6 7 8 9 Last 
青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            亚洲一区在线免费观看| 国产精品久久久久久一区二区三区 | 午夜精品久久一牛影视| 一本色道久久综合精品竹菊 | 欧美v国产在线一区二区三区| 久久九九久精品国产免费直播| 久久精品视频播放| 麻豆国产va免费精品高清在线| 欧美jizz19性欧美| 欧美三区美女| 黄色亚洲在线| 99国产精品国产精品毛片| 亚洲一区不卡| 久久夜色精品国产亚洲aⅴ| 欧美激情一区二区三区在线| 亚洲国内在线| 国产精品99久久久久久久vr| 欧美一乱一性一交一视频| 美女视频网站黄色亚洲| 欧美日韩在线综合| 激情久久一区| 亚洲一区二区三区欧美 | 亚洲精品乱码| 久久高清免费观看| 欧美美女操人视频| 精品成人国产| 亚洲制服av| 亚洲国产成人不卡| 午夜在线电影亚洲一区| 欧美日本在线一区| 激情成人中文字幕| 欧美一区二区三区喷汁尤物| 亚洲激情在线观看视频免费| 欧美在线观看日本一区| 国产精品theporn88| 亚洲国产裸拍裸体视频在线观看乱了中文 | 久久久久久久久久久久久9999 | 欧美日韩精品久久久| 国产欧美在线观看一区| 亚洲欧洲综合| 久久久久久色| 亚洲影院色无极综合| 欧美精品在线观看| 亚洲国产精品久久人人爱蜜臀| 欧美一区三区三区高中清蜜桃 | 久久激情五月婷婷| 国产精品视频你懂的| 一区二区三区久久久| 欧美激情一区二区三区在线| 久久久99国产精品免费| 国产精品日韩精品欧美精品| 在线亚洲观看| 亚洲美女视频在线观看| 欧美激情一区在线| 亚洲精品美女| 亚洲欧洲日本国产| 欧美精品亚洲一区二区在线播放| 亚洲国产精品久久久久秋霞不卡 | 精品96久久久久久中文字幕无| 亚洲欧美中文字幕| 亚洲一区二区三区国产| 国产精品久久久久久久免费软件 | 欧美高清视频一二三区| 久久国产欧美日韩精品| 国产亚洲人成网站在线观看| 亚洲欧美国产视频| aa国产精品| 国产日韩精品一区二区| 欧美在线91| 久久久精品动漫| 91久久中文| 亚洲国产精品一区二区久| 久久夜色精品国产噜噜av| 韩国欧美一区| 亚洲国产精彩中文乱码av在线播放| 亚洲欧美在线另类| 国产偷久久久精品专区| 久久久精彩视频| 亚洲在线观看视频网站| 国产亚洲午夜高清国产拍精品| 你懂的视频欧美| 欧美激情一区二区三区蜜桃视频| 亚洲看片一区| 亚洲视频一区在线观看| 国产一区二区三区av电影| 久久久久久有精品国产| 欧美一区二区在线观看| 伊人久久成人| 亚洲激情网站| 一本色道久久综合一区| 99精品热6080yy久久| 国产日韩欧美夫妻视频在线观看| 久久久久九九九| 美女主播一区| 亚洲免费在线播放| 久久精品久久综合| 亚洲精品一区在线观看| 亚洲免费激情| 国产精品午夜在线观看| 欧美国产综合视频| 国产欧美日韩一区二区三区| 久久婷婷色综合| 欧美日韩一区二区在线视频 | 亚洲精美视频| 国产精品一区二区你懂得| 欧美不卡福利| 国产精品尤物福利片在线观看| 欧美不卡在线视频| 国产精品免费在线 | 久久精品国产一区二区三区免费看| 亚洲国产另类久久久精品极度| 亚洲午夜久久久久久久久电影网| 在线观看中文字幕不卡| 亚洲欧美另类在线观看| 一个人看的www久久| 久久成人资源| 午夜精品三级视频福利| 欧美搞黄网站| 久久一二三四| 国产欧美一级| 亚洲在线黄色| 午夜免费久久久久| 欧美日韩国产高清| 亚洲精品美女在线观看播放| 亚洲国产一区二区三区a毛片| 久久精品国产精品亚洲| 久久精品一级爱片| 国产区二精品视| 亚洲午夜精品久久久久久浪潮 | 亚洲激情第一区| 在线成人小视频| 欧美专区在线观看| 久久久久久午夜| 国模套图日韩精品一区二区| 亚洲一区在线视频| 亚洲欧美另类中文字幕| 国产精品av久久久久久麻豆网| 亚洲精品日本| 在线亚洲成人| 欧美视频二区| 亚洲一级特黄| 久久高清免费观看| 狠狠色狠狠色综合日日tαg| 久久国产婷婷国产香蕉| 免费不卡在线观看av| 亚洲激情电影中文字幕| 欧美日韩播放| 一区二区三区视频免费在线观看| 99日韩精品| 亚洲欧美日韩专区| 国产视频一区免费看| 午夜精品久久久久久久久久久久 | 亚洲综合大片69999| 亚洲尤物在线视频观看| 久久久99免费视频| 在线精品国精品国产尤物884a| 久久婷婷综合激情| 亚洲片区在线| 午夜在线电影亚洲一区| 黄色亚洲在线| 欧美精品亚洲| 午夜视频一区在线观看| 裸体丰满少妇做受久久99精品| 亚洲区一区二| 国产精品久久久久久久7电影| 欧美亚洲免费高清在线观看| 欧美激情视频一区二区三区免费 | 亚洲一级电影| 国产三级欧美三级日产三级99| 久久精品国产91精品亚洲| 亚洲国产精品ⅴa在线观看| 亚洲自拍电影| 亚洲高清影视| 国产精品亚发布| 免费成人黄色片| 亚洲一区二区在线视频| 暖暖成人免费视频| 亚洲一区网站| 亚洲第一狼人社区| 国产精品视频午夜| 免费一区二区三区| 欧美一级视频一区二区| 日韩亚洲在线| 免费在线观看精品| 亚洲欧美综合| 夜夜嗨av一区二区三区网站四季av| 国产精品一二三视频| 欧美大尺度在线| 久久精品亚洲一区二区三区浴池| 夜夜嗨一区二区三区| 亚洲电影网站| 久久夜色精品亚洲噜噜国产mv| 亚洲欧美日韩在线综合| 亚洲精品中文在线| 在线观看成人av电影| 国产欧美一区二区精品仙草咪| 欧美日韩在线一区二区| 欧美极品aⅴ影院| 久久免费视频在线观看| 亚洲少妇自拍|