Unity 基礎知識點

1、委托是什么,事件是委托嗎? 它們有什么區(qū)別?

C#中委托通常是指委托類型創(chuàng)建的對象,它用于保存和調(diào)用同類型的方法,基于它可以很方便地實現(xiàn)觀察者模式。事件不是委托,是委托的更安全實現(xiàn),也用于保存和調(diào)用同類型的方法,安全性體現(xiàn)在:事件對象不支持=操作符,以及只能在定義事件的類中,調(diào)用事件內(nèi)所保存的方法

2、運行string a = new string(”XYZ”);代碼時,涉及幾個String對象?

2個,一個是字符串字面量"xyz"所對應的、駐留在一個全局共享的字符串常量池中的實例對象,另一個是通過new String(String)創(chuàng)建并初始化的、內(nèi)容與"xyz"相同的實例對象。a是string類型的引用變量,非實例對象。

3、值類型與引用類型的區(qū)別?

在C#中,基于值類型創(chuàng)建變量時,會創(chuàng)建相應類型的對象,并用變量名進行標識,可直接用于存儲數(shù)據(jù),其對象內(nèi)存一般位于棧區(qū)。

而基于引用類型創(chuàng)建變量時,其變量為引用變量,并沒有創(chuàng)建引用類型的對象。引用類型的變量,需要引向堆區(qū)的引用類型對象,通過它將數(shù)據(jù)存放到堆區(qū)對象。

4、腳本生命周期從開始到結(jié)束,寫出幾種系統(tǒng)調(diào)用的方法?

Awake、OnEnable、Reset、Start、FixedUpdate、Update、LateUpdate、OnGUI、OnApplicationPause、OnApplicationQuit、OnDisable、OnDestroy

[if !supportLists](1)?? [endif]Awake(用于在游戲開始之前初始化變量或游戲狀態(tài),用Awake來設置腳本間的引用,能用來執(zhí)行協(xié)同程序)

[if !supportLists](2)??[endif]Start(函數(shù)只在腳本實例被啟用時才會執(zhí)行,如果游戲?qū)ο箝_啟了,對象上綁定的腳本實例被禁用了,那么Start函數(shù)不會執(zhí)行。并且Start函數(shù)只會在腳本實例首次被開啟時才會執(zhí)行。如果是已經(jīng)開啟過的腳本實例被關閉后再次開啟,那么Start函數(shù)不會再次執(zhí)行)

[if !supportLists](3)?? [endif]Update(正常幀更新,用于更新邏輯。每一幀都執(zhí)行,ixedUpdate比較適用于物理引擎的計算,因為是跟每幀渲染有關。Update就比較適合做控制。)

[if !supportLists](4)?? [endif]FixedUpdate(固定幀更新,其中“Fixed?Timestep”選項用于設置FixedUpdate()的更新頻率,更新頻率默認為0.02)

[if !supportLists](5)?? [endif]LateUpdate:在所有Update函數(shù)調(diào)用后被調(diào)用,和fixedupdate一樣都是每一幀都被調(diào)用執(zhí)行,這可用于調(diào)整腳本執(zhí)行順序,LateUpdate,在每幀Update執(zhí)行完畢調(diào)用,他是在所有update結(jié)束后才調(diào)用,比較適合用于命令腳本的執(zhí)行。

[if !supportLists](6)?? [endif].OnGUI:在渲染和處理GUI事件時調(diào)用,每幀執(zhí)行一次。

[if !supportLists](7)?? [endif]Reset:(在用戶點擊檢視面板的Reset按鈕或者首次添加該組件時被調(diào)用。此函數(shù)只在編輯模式下被調(diào)用。Reset最常用于在檢視面板中給定一個默認值。)

[if !supportLists](8)?? [endif]OnDisable:(當物體被銷毀時 OnDisable將被調(diào)用,并且可用于任意清理代碼。腳本被卸載時,OnDisable將被調(diào)用,OnEnable在腳本被載入后調(diào)用。注意: OnDisable不能用于協(xié)同程序。)

[if !supportLists](9)?? [endif]OnDestroy:當MonoBehaviour將被銷毀時,這個函數(shù)被調(diào)用。OnDestroy只會在預先已經(jīng)被激活的游戲物體上被調(diào)用。注意:OnDestroy也不能用于協(xié)同程序。

[if !supportLists](10) [endif]OnEnable:腳本組件被激活的時候運行,且每次被重新激活,都會運行一次

GameObject的Activity為true,腳本的enable為true時,其先后順序為:Awake、OnEnable、Start;

GameObject

的Activity為true,腳本的enable為false時,只運行Awake;

GameObject的Activity為false時,以上都不調(diào)用,OnDisable()被調(diào)用;

Awake --> OnEnable -->?Start --> Update --> FixedUpdate -->

LateUpdate -->OnGUI --> OnDisable -->OnDestroy

5、資源動態(tài)加載的方式有哪幾種?

1)通過Resources模塊的load方法,可以直接load并返回某個類型的Object,前提是要把這個資源放在Resource命名的文件夾下,Unity不關有沒有場景引用,都會將其全部打入到安裝包中。

(2)通過AssetBundle的形式:即將資源打成 asset bundle 放在服務器或本地磁盤,然后使用www模塊get 下來,然后從這個bundle中l(wèi)oad某個object。

(3)通過AssetDatabase.loadasset:這種方式只在editor范圍內(nèi)有效,游戲運行時沒有這個函數(shù),它通常是在開發(fā)中調(diào)試用的

6、ArrayList 與List<Int>的區(qū)別?

ArrayList是非泛型集合類,不是類型安全的。ArrayList在管控對象時,需要保證其為object類型的子類。在使用對象時,還需要將它們轉(zhuǎn)化為對應的原類型來處理。期間,容易出現(xiàn)類型不匹配的情況。另外,在管控和使用對象時,還可能存在了裝箱與拆箱的操作,會帶來很大的性能損耗。

List<Int>是泛型集合,不存在裝箱與拆箱和類型安全的問題,C#中推薦使用泛型集合。

7、LOD是什么,優(yōu)缺點。LOD是什么,優(yōu)缺點?

LOD全稱是Level of Detail,也就是細節(jié)層級。LOD是一個用于性能優(yōu)化的方案,它根據(jù)物體與攝像機的距離來展示這個物體不同的mesh,從而使得物體較遠是使用面數(shù)比較少的mesh,而距離近的時候使用面數(shù)多的mesh。

缺點是:需要占用更多的內(nèi)存,而且如果沒有調(diào)整好距離的話,可能會造成模擬的突變。

8、哪些情況下,Unity3D 中會發(fā)生在組件上出現(xiàn)數(shù)據(jù)丟失的情況?

組件上引用的資源被刪除,常出現(xiàn)在:工程間進行數(shù)據(jù)遷移;在資源視圖誤刪資源。

9、MeshRenderer中有屬性.material,以及.sharedMaterial。兩者有什么區(qū)別?

sharedMaterial 是共用的 Material,稱為共享材質(zhì)。修改共享材質(zhì)會改變所用使用該材質(zhì)的物體,并且編輯器中的材質(zhì)設置也會改變。

material 是獨立的 Material,返回分配給渲染器的第一個材質(zhì)。修改材質(zhì)僅會改變該物體的材質(zhì)。如果該材質(zhì)被其他的渲染器使用,將克隆該材質(zhì)并用于當前的渲染器。

10、當camera距離一個模型很近,靠近攝像機的mesh出現(xiàn)部分丟失,應該如何優(yōu)化這種現(xiàn)象。

拉近攝像機的近裁剪面。

11、簡述Unity的協(xié)同程序,并寫出任意一個示例程序。

unity協(xié)程是一個能暫停執(zhí)行,暫停后立即返回,直到中斷指令完成后繼續(xù)執(zhí)行的函數(shù)。它類似一個子線程單獨出來處理一些問題,性能開銷較小,但是他在一個MonoBehaviour提供的主線程里只能有一個處于運行狀態(tài)的協(xié)程。

12.如何理解消息機制,你用過哪些消息事件系機制?請簡單描述一下消息機制的實現(xiàn)方法。(最好用代碼或者偽代碼設計出來一個簡單的消息機制)。

消息機制的主要作用是解耦和。消息的發(fā)送者不需要了解接收者的具體情況,完全零耦合??梢曰谑录磉M行消息的監(jiān)聽,內(nèi)部用Dictinary進行保存事件和消息一一對應,將委托添加到對應事件的監(jiān)聽中,發(fā)送消息時,對Dictinary對應的事件進行調(diào)用即可。

13、你覺得在FPS里哪些東西適合使用對象池,請簡述一下對象池。

在FPS游戲中,經(jīng)常被大量創(chuàng)建的同類型對象,包括子彈,敵人,粒子等,都適合使用對象池進行管理。

unity中一些需要頻繁創(chuàng)建和銷毀的對象,在銷毀時會頻繁的調(diào)用gc,非常占用cpu時,造成性能瓶頸。這時候就需要對象池技術。使用對象池在銷毀時并不調(diào)用gc,而是僅僅將需要銷毀的obj失活,當再次創(chuàng)建同類對象時,在對象池中查找可以使用的對象進行調(diào)用。僅僅在需要的時候調(diào)用gc進行一次銷毀。這樣做大大減少了cpu的壓力,但是增大了內(nèi)存的消耗,通常情況這種犧牲是值得的。

14、常見的Unity的優(yōu)化主要有哪些,著重點是那些?

使用LOD、Mipmap提供渲染速度。注意:Mipmap類似于LOD,但LOD是針對于模型來處理,Mip是針對貼圖紋理來處理。

對象池,提高游戲性能;數(shù)據(jù)緩存層設計,提高資源加載速度;

使用光照探頭或 烘培靜態(tài)光照貼圖,提高光照渲染效率;

紋理圖集合并,減少DC;

恰當使用Unity提供的靜態(tài)合并和動態(tài)合并方式,減少DC。

在拼接或連接大量字符串時,需使用StringBuilder,減少GC。

15、在Unity中使用線程有什么要注意的?

unity中使用c#的多線程時不能使用修改unity相關函數(shù)、屬性,使用時Unity會報錯提示。當需要進行修改位置,旋轉(zhuǎn)之類的操作時,可以創(chuàng)建一個單例Mono類對象,開啟協(xié)程。操作需要在Unity主線程中的操作函數(shù)時,對該單例類添加一個委托,在單例類協(xié)程中持續(xù)判斷委托。如果存在委托就執(zhí)行并且清空。

僅能從主線程中訪問Unity3D的組件,對象和Unity3D系統(tǒng)調(diào)用支持。如果同時你要處理很多事情或者且與Unity的對象互動少,可以用thread,否則使用coroutine。注意:C#中有l(wèi)ock這個關鍵字,用來確保只有一個線程可以在特定時間內(nèi)訪問特定的對象。

16、使用mipmap有什么好處和壞處?什么情況下使用?

Mipmap,稱為多級漸進紋理。為了加快渲染速度和減少紋理鋸齒,貼圖被處理成由一系列被預先計算和優(yōu)化過的圖片組成的文件,這樣的貼圖被稱為Mipmap。常用于:根據(jù)攝像機距離模型的遠近而調(diào)整使用不同質(zhì)量的貼圖。

[if !vml]

[endif]?

Mipmap寬高值不一定要相等,但需要為2的n次冪,最低精度為1x1;從原始高精度的Mipmap寬高減半,逐級生成低精度的Mipmap層級;所有低精度層級加起來,會增加1/3存儲空間的占用:A、Mipmap貼圖文件占用更多硬盤空間,解決方法:使用dds進行壓縮存儲。B、Mipmap紋理占用更多內(nèi)存、顯存空間。

17、手寫除了冒泡外的,你已知的排序算法。

常見:快速排序,堆排序,插入排序等。

18、請簡述GC(垃圾回收)產(chǎn)生的原因,并描述何如避免?

當我用new創(chuàng)建一個對象時,當可分配的內(nèi)存不足GC就會去回收未使用的對象,但是GC的操作是非常復雜的,會占用很多CPU時間,對于移動設備來說頻繁的垃圾回收會嚴重影響性能。

下面的建議可以避免GC頻繁操作。

減少用new創(chuàng)建對象的次數(shù),在創(chuàng)建對象時會產(chǎn)生內(nèi)存碎片,這樣會造成碎片內(nèi)存不法使用

使用公用的對象(靜態(tài)成員,常量),但是不能亂用,因為靜態(tài)成員和常量的生命周期是整個應用程序。

在拼接大量字符串時StringBuilder。在使用注意,創(chuàng)建StringBuilder對象時要設置StringBuilder的初始大小如:StringBuilder sb1

=new StringBuilder (size);

使用object pool(對象池)

19、時間復雜度和空間復雜度,是什么?給出冒泡排序和快速排序的時間和空間復雜度

算法的時間復雜度(Time Complexity),用來 衡量算法執(zhí)行時所需“時間”,它是對 【程序基本操作重復執(zhí)行的次數(shù)與問題規(guī)模n的函數(shù)f(n)】進行【O()運算】的結(jié)果,常記為T(n)

算法的空間復雜度(Space Complexity),是對一個算法在運行過程中【臨時額外】占用存儲空間大小的量度,常記為 S(n) 。它是 對 【額外空間與問題規(guī)模n的函數(shù)f(n)】 進行【O()運算】的結(jié)果。

?時間復雜度空間復雜度

冒泡排序O(n2)O(1)

快速排序O(n2)O(nlog2n)

直接插入O(n2)O(1)


20、有兩段代碼if(go.CompareTag(“Enemy”)) 和if(go.tag==”Enemy”)有什么區(qū)別?

go.CompareTag調(diào)用一次內(nèi)部方法就完成了比較,但go.tag要先花時間調(diào)用一次getter來獲得字符串,消耗的時間相比CompareTag會更多。建議,使用CompareTag替換所有的tag。

21、已知道List<int> list1=new

List<int>(new int[](1,2,3,4,5)),請問,如果用foreach操作lst1,有什么需要注意的?

使用foreach遍歷容集合時,可以得到對象的標識符或引用。但是無法增加、刪除,修改,該集合對象所管控的元素。

22、string tmp = "你好,我愛編程?。?;,請C#編程實現(xiàn)截出“我愛編程”;

string ret1 = tmp.Substring(3, 4); ?

//C#中char型是2個字節(jié),一個char變量可以存放一個漢字。

// string類的其他常見方法見 文字課件。

23、寫出UGUI中監(jiān)聽事件的幾種方式

在腳本代碼中,使用代碼,添加事件監(jiān)聽,比如:onClick.addListener等;

在腳本組件的檢視視圖中,手動添加事件監(jiān)聽的對象,并設置回調(diào)函數(shù);

在腳本代碼中,繼承相關事件的接口,實現(xiàn)對事件的監(jiān)聽,比如:IBeginDrag等。

24、四元數(shù)的作用,四元數(shù)對歐拉角的優(yōu)點?基于偽代碼:給出基于四元數(shù),緩慢旋轉(zhuǎn)到指定朝向(使用Vector3表示)的實現(xiàn)

四元數(shù)和歐拉角,均用于表示物體的朝向,在unity中分別使用Quaternion類和Vector3類進行描述和實現(xiàn)。

歐拉角在表示物體朝向時,優(yōu)點是:容易理解和形象直觀,缺點是:在兩個歐拉角之間,無法做插值運算;對于一個給定的朝向,表示方式不唯一;有萬向節(jié)死鎖(Gimbal Lock)的現(xiàn)象。

四元數(shù),在表示物體朝向時,優(yōu)點是:可以避免萬向節(jié)鎖現(xiàn)象,可以提供平滑插值;某些情況下,使用四元數(shù)實現(xiàn)旋轉(zhuǎn),更加高效。缺點是:理解困難,不直觀;

實現(xiàn)代碼:

????? Quaternion dstRotation =Quaternion.LookRotation(dstDirection, Vector3.up);

this.transform.rotation =Quaternion.Slerp(transform.rotation, dstRotation, Time.deltaTime * 2.0f);

25、什么是渲染管道 或 渲染管線?

渲染管線是指為了在顯示器上,顯示出圖像而經(jīng)過的一系列必要操作。渲染管道中的很多步驟,都要將幾何物體從一個坐標系中變換到另一個坐標系中去。主要步驟有:本地坐標->視圖坐標->背面裁剪->光照->裁剪->投影->視圖變換->光柵化。

[if !vml]

[endif]?

具體參見《Shader入門精要》。

26、談談shader的類型和各自在什么時候使用。通常Shader中是如何將圖片變成灰度圖。

Shader按管線分類一般分為固定渲染管線與可編程渲染管線。

1、固定渲染管線

這是標準的幾何&光照(Transforming&Lighting)管線,功能是固定的,它控制著世界、視、投影變換及固定光照控制和紋理混合。T&L管線可以被渲染狀態(tài)控制,矩陣,光照和采制參數(shù)。功能比較有限?;舅械娘@卡都能正常運行。

2、可編程渲染管線

對渲染管線中的頂點運算和像素運算分別進行編程處理,而無須象固定渲染管線那樣套用一些固定函數(shù),取代設置參數(shù)來控制管線。

27、Unity3d的三種Shader:

1、固定功能著色器(Fixed Function Shader)

固定功能著色器為固定功能渲染管線的具體表現(xiàn)。功能較簡單兼容比較老的機器

2、頂點和片段著色器(Vertex and Fragment Shader)

最強大的Shader類型,屬于可編程渲染管線, 使用的是CG/HLSL語法。

3、表面著色器(Surface Shade)

Unity3d推崇的Shader類型,使用Unity預制的光照模型來進行光照運算。使用的也是CG/HLSL語法。

圖片灰度化:

修改對應Shader中的灰色公式,設置為:Gray = R*0.299 + G*0.587 +

B*0.114,即可實現(xiàn)圖片變灰的效果。比如:UGUI中彩色UI變灰色,找到UI-Default.shader,復制,重命名為UI-Gray.shader, 將frag函數(shù)修改為如上參數(shù)即可。

28、Unity3D Shader分為哪幾種,有什么區(qū)別?

1、表面著色器,的抽象層次比較高,它可以輕松地以簡潔方式實現(xiàn)復雜著色。表面著色器可同時在前向渲染及延遲渲染模式下正常工作。

2、頂點片段著色器,可以非常靈活地實現(xiàn)需要的效果,但是需要編寫更多的代碼,并且很難與Unity的渲染管線完美集成。

3、固定功能管線著色器,可以作為前兩種著色器的備用選擇,當硬件無法運行那些酷炫Shader的時,還可以通過固定功能管線著色器來繪制出一些基本的內(nèi)容。

29、在VR游戲中,前向渲染和延遲渲染應該選擇哪一個,為什么?

前向渲染 提供更快的基線和更快的渲染通道,可在 VR 平臺擁有更好的性能。前向渲染不僅速度更快,相較于延遲渲染器它還擁有更多抗鋸齒選項,帶來更為清晰明快的顯示效果。

//以下了解

[if !vml]

[endif]?

Forward Rendering(正向渲染/前向渲染)是大多數(shù)渲染引擎使用的渲染技術。你給顯卡提供幾何對象,它將幾何對象分解成頂點送入頂點著色器,然后把這些頂點數(shù)據(jù)插值后分別送入片元/像素著色器,然后在它們被送入屏幕前做最終的渲染處理(模板測試,混合等)。

[if !vml]

[endif]?

Deferred Rendering(延遲渲染),從這個名字來看就意味著渲染是被延遲的,直到所有幾何對象都已經(jīng)通過渲染管線處理后,在最后才應用著色(通過光照來決定最終的像素顏色)并產(chǎn)生最終的圖像。

[if !vml]

[endif]?


30、什么是drawcall?敘述下Unity3d中的drawcall合并

在使用unity的時候經(jīng)常會要求盡量降低Draw call和Batched 的數(shù)量。那么Draw call 和Batched 到底指的是什么呢?

Draw Call: Unity生成一幀的畫面的處理過程大致過程是:

引擎經(jīng)過可見性測試,確定攝像機可以看到的物體,然后把這些物體的頂點(包括頂點位置、法線、uv 等),索引(如何組成三角形),變換(物體的位置旋轉(zhuǎn) 縮放 以及攝像機的位置)相關光源,紋理,渲染方式(由材質(zhì)/Shader決定)等數(shù)據(jù)準備好,然后通知圖形API(或者就簡單地看作是通知GPU)開始繪制,GPU基于這些數(shù)據(jù)經(jīng)過一些列的運算,在屏幕上畫出組成圖形的三角形,構成一幅畫。

在unity 中每次引擎裝備數(shù)據(jù)并通知GPU的過程為一次Draw Call。

為什么要優(yōu)化DrawCall?

因為通知給GPU這個工作是由CPU來完成的,完成每一次DrawCall都需要CPU完成很多的內(nèi)容,因此如果DrawCall很多的話CPU一定是不堪重負。但對于GPU而言,很多的工作都是一樣的,也就是說很多的DrawCall是沒有意義的,可以理解為很多次的DrawCall都可以合并為一次,這樣減輕了CPU的負擔,同樣也可以通知GPU完成相應的工作。因此減少DrawCall成了優(yōu)化CPU的第一要務。

Batched: Batched 其實是Draw Call的另外一種稱呼。你可以想象成 每一次的Draw Call 是CPU把一個Batched里的數(shù)據(jù)(物體的頂點數(shù)據(jù))傳輸給GPU,由GPU繪制到屏幕上。因此Batched越多需要傳輸?shù)臄?shù)據(jù)就越多,產(chǎn)生的Draw Call也會越多,也會消耗更多的性能。

Unity提供了Dynamic Batching和Static

Batching兩種方式。

//具體見https://docs.unity3d.com/Manual/DrawCallBatching.html

31、如何優(yōu)化內(nèi)存

代碼級別優(yōu)化:

1、連接兩個字符串的操作使用StringBuilder.Append來代替string。

2、使用gameObject.CompareTag("XXX")來代替gameObject.tag = xxx。

3、使用ObjectPool對象池來管理對象,避免頻繁使用的Instance,Destroy。

//其他補充

//https://blog.csdn.net/wwanrong/article/details/78676275

//https://www.bbsmax.com/R/ke5jG4Xdrl/

//http://m.itdecent.cn/p/14b978447135

32、寫光照計算中diffuse的計算公式

實際光照強度 I= 環(huán)境光 (Iambient) + 漫反射光 (Idiffuse) + 鏡面高光(Ispecular);

環(huán)境光:Iambient= Aintensity* Acolor; (Aintensity 表示環(huán)境光強度,Acolor 表示環(huán)境光顏色)

漫反射光:Idiffuse = Dintensity*Dcolor*N.L;

(Dintensity 表示漫反射強度, Dcolor 表示漫反射光顏色, N 為該點的法向量, L 為光源向量)

鏡面反射光:Ispecular = Sintensity*Scolor*(R.V)^n;

(Sintensity 表示鏡面光照強度, Scolor 表示鏡面光顏色, R 為光的反射向量, V 為觀察者向量, n 稱為鏡面光指數(shù))

引用類型的基類System.Object

值類型的基類System.ValueType

34.Interface 與抽象類之間的不同

答:抽象類表示該類中可能已經(jīng)有一些方法的具體定義,但接口就是公公只能定義各個方法的界面,不能具體的實現(xiàn)代碼在成員方法中。

類是子類用來繼承的,當父類已經(jīng)有實際功能的方法時該方法在子類中可以不必實現(xiàn),直接引用父類的方法,子類也可以重寫該父類的方法。

實現(xiàn)接口的時候必須要實現(xiàn)接口中所有的方法,不能遺漏任何一個。

35. 請簡述 ArrayList 和 List 的主要區(qū)別

答: ArrayList存在不安全類型 ‘ ( ArrayList 會把所有插入其中的數(shù)據(jù)都當做 Object 來處理)

裝箱拆箱的操作(費時)List 是接口, ArrayList 是一個實現(xiàn)了該接口的類,可以被實例化。

36.Unity3D 的協(xié)程和 C# 線程之間的區(qū)別是什么?

多線程程序同時運行多個線程 ,而在任一指定時刻只有一個協(xié)程在運行,并且這個正在運行的協(xié)同程序只在必要時才被掛起。除主線程之外的線程無法訪問 Unity3D 的對象、組件、方法。 Unity3d 沒有多線程的概念,不過 unity 也給我們提供了StartCoroutine (協(xié)同程序)和 LoadLevelAsync (異步加載關卡)后臺加載場景的方法。StartCoroutine 為什么叫協(xié)同程序呢,所謂協(xié)同,就是當你在 StartCoroutine 的函數(shù)體里處理一段代碼時,利用 yield 語句等待執(zhí)行結(jié)果,這期間不影響主程序的繼續(xù)執(zhí)行,可以協(xié)同工作。而LoadLevelAsync 則允許你在后臺加載新資源和場景,所以再利用協(xié)同,你就可以前臺用 loading 條或動畫提示玩家游戲未卡死,同時后臺協(xié)同處理加載的事宜 asynchronous[e ?? s ?? kr ? n ? s] .synchronous 同步。??

37. 簡述四元數(shù)的作用,四元數(shù)對歐拉角的優(yōu)點?

答:四元數(shù)用于表示旋轉(zhuǎn)

相對歐拉角的優(yōu)點: 1 )能進行增量旋轉(zhuǎn) 2 )避免萬向鎖 3 )給定方位的表達方式有兩種,互為負(歐拉角有無數(shù)種表達方式)

38. 矩陣相乘的意義及注意點

用于表示線性變換:旋轉(zhuǎn)、縮放、投影、平移、仿射

注意矩陣的蠕變:誤差的積累

39. 向量的點乘、叉乘以及歸一化的意義?

1 )點乘描述了兩個向量的相似程度,結(jié)果越大兩向量越相似,還可表示投影 2 )叉乘得到的向量垂直于原來的兩個向量 3 )標準化向量:用在只關系方向,不關心大小的時候

40.為什么 dynamic font 在 unicode 環(huán)境下優(yōu)于static font

Unicode 是國際組織制定的可以容納世界上所有文字和符號的字符編碼方案。

使用動態(tài)字體時,Unity 將不會預先生成一個與所有字體的字符紋理。當需要支持亞洲語言或者較大的字體的時候,若使用正常紋理,則字體的紋理將非常大。

41. 為什么 Unity3D 中會發(fā)生在組件上出現(xiàn)數(shù)據(jù)丟失的情況?

答:組件上綁定的對象被刪除了

42.如何安全的在不同工程間安全地遷移 asset 數(shù)據(jù)?三種方法

答:將 Assets 目錄和 Library 目錄一起遷移

導出包用 unity 自帶的 assets Server 功能

43.請描述游戲動畫有哪幾種,以及其原理

主要有關節(jié)動畫、單一網(wǎng)格模型動畫 ( 關鍵幀動畫 ) 、骨骼動畫。

關節(jié)動畫把角色分成若干獨立部分,一個部分對應一個網(wǎng)格模型,部分的動畫連接成一個整體的動畫,角色比較靈活 Quake2 中使用了這種動畫。

單一網(wǎng)絡模型動畫由一個完整的網(wǎng)格模型構成,在動畫序列的關鍵幀里記錄各個頂點的原位置及其改變量,然后插值運算實現(xiàn)動畫效果,角色動畫較真實。

骨骼動畫,廣泛應用的動畫方式,集成了以上兩個方式的優(yōu)點,骨骼按角色特點組成一定的層次結(jié)構,由關節(jié)相連,可做相對運動,皮膚作為單一網(wǎng)格蒙在骨骼之外,決定角色的外觀。皮膚網(wǎng)格每一個頂點都會受到骨骼的影響,從而實現(xiàn)完美的動畫。(骨骼動畫是由關節(jié)動畫發(fā)展而來的,如今基本都使用骨骼動畫來實現(xiàn)角色動畫)

44.兩種陰影判斷的方法工作原理

陰影由兩部分組成:本影與半影

本影:景物表面上那些沒有被光源直接照射的區(qū)域(全黑的輪廓分明的區(qū)域)

半影:景物表面上那些被某些特定光源直接照射但并非被所有特定光源直接照射的區(qū)域(半明半暗區(qū)域)

求陰影區(qū)域的方法:做兩次消隱過程

一次對每個光源進行消隱,求出對于光源而言不可見的區(qū)域 L ;

一次對視點的位置進行消隱,求出對于視點而言可見的面S

shadow area= L ∩S

陰影分為兩種:自身陰影和投射陰影

自身陰影:因物體自身的遮擋而使光線照射不到它上面的某些可見面

工作原理:利用背面剔除的方法求出,即假設視點在點光源的位置。

投射陰影:因不透明物體遮擋光線使得場景中位于該物體后面的物體或區(qū)域受不到光照照射而形成的陰影

工作原理:從光源處向物體的所有可見面投射光線,將這些面投影到場景中得到投影面,再將這些投影面與場景中的其他平面求交得出陰影多邊形,保存這些陰影多邊形信息,然后再按視點位置對場景進行相應處理得到所要求的視圖(利用空間換時間,每次只需依據(jù)視點位置進行一次陰影計算即可,省去了一次消隱過程)

若是動態(tài)光源此方法就無效了。

45.Vertex

Shader是什么?怎么計算?

頂點著色器是一段執(zhí)行在GPU 上的程序,用來取代 fixed pipeline 中的transformation和 lighting , Vertex Shader 主要操作頂點。

Vertex Shader 對輸入頂點完成了從 local space 到 homogeneous space (齊次空間)的變換過程, homogeneous

space 即 projection space 的下一個space 。在這其間共有 world transformation, view transformation和 projection transformation 及l(fā)ighting幾個過程。

46.用u3d實現(xiàn)2d游戲,有幾種方式?

?? 1.利用引擎自帶的GUI

?? 2.把攝像機設為 Orthographic ,用面片作為 2d 元素

?? 3.利用第三方插件: NGUI 、2dToolkit

47.CharacterController和Rigidbody的區(qū)別

Rigidbody 具有完全真實物理的特性,而 CharacterController 可以說是受限的Rigidbody ,具有一定的物理效果但不是完全真實的。

48.u3d中,幾種施加力的方式,描述出來

rigidbody.AddForce/AddForceAtPosition,都是 rigidbody 的成員函數(shù)

49.unity3d提供了幾種光源,分別是什么

平行光:Directional Light

聚光燈:SpotLight

點光源:PointLight

區(qū)域光源: Area

Light (只用于烘培)

50.u3d提供了一個用于保存讀取數(shù)據(jù)的類,(playerPrefs),請列出保存讀取整形數(shù)據(jù)的函數(shù)

PlayerPrefs.SetInt與PlayerPrefs.GetInt

51.移動相機動作在哪個函數(shù)里,為什么在這個函數(shù)里。

LateUpdate, ,是在所有 update 結(jié)束后才調(diào),比較適合用于命令腳本的執(zhí)行。官網(wǎng)上例子是攝像機的跟隨,都是在所有 update 操作完才跟進攝像機,不然就有可能出現(xiàn)攝像機已經(jīng)推進了,但是視角里還未有角色的空幀出現(xiàn)。

52.當游戲中需要頻繁創(chuàng)建一個物體對象時,我們需要怎么做來節(jié)省內(nèi)存。

做一個 pool ,游戲開始時預先實例化足夠的數(shù)量,然后用的時候取不用的時候收回

53.一個場景放置多個camera并同時處于活動狀態(tài),會發(fā)生什么

實際看到的畫面由多個camera 的畫面組成,由 depth 、 Clear

Flag 、 Culling Mask都會影響最終合成效果。

54.什么叫做鏈條關節(jié)

Hinge Joint ,他可以模擬兩個物體間用一根鏈條連接在一起的情況,能保持兩個物體在一個固定距離內(nèi)部相互移動而不產(chǎn)生作用力,但是達到固定距離后就會產(chǎn)生拉力。(簡單說就是彈簧)

55.物體自旋轉(zhuǎn)使用的函數(shù)叫什么transform.Rotate

56.物體繞某點旋轉(zhuǎn)使用函數(shù)叫什么transform.RotateAround

57.什么是渲染管道?

是指在顯示器上為了顯示出圖像而經(jīng)過的一系列必要操作。 渲染管道中的很多步驟,都要將幾何物體從一個坐標系中變換到另一個坐標系中去。

主要步驟有:

本地坐標 -> 視圖坐標 -> 背面裁剪 -> 光照-> 裁剪 -> 投影 -> 視圖變換 -> 光柵化。

58.如何優(yōu)化內(nèi)存?

1. 壓縮自帶類庫;

2. 將暫時不用的以后還需要使用的物體隱藏起來而不是直接 Destroy 掉;

3. 釋放 AssetBundle 占用的資源;

4. 降低模型的片面數(shù),降低模型的骨骼數(shù)量,降低貼圖的大小;

5. 使用光照貼圖,使用多層次細節(jié) (LOD) ,使用著色器 (Shader) ,使用預設(Prefab) 。

59、動態(tài)加載資源的方式?

1.Resources.Load();

2.AssetBundle

60.Animation.CrossFade命令作用是:(動畫的淡入為其他動畫)

61.Application.loadLevel命令為:(加載關卡)

62. 使用原生 GUI 創(chuàng)建一個可以拖動的窗口命令是什么?GUI.DragWindow();

63,在類的構造函數(shù)前加上static會報什么錯?為什么?

構造函數(shù)格式為public+ 類名如果加上 static 會報錯(靜態(tài)構造函數(shù)不能有訪問修飾符)

原因:靜態(tài)構造函數(shù)不允許訪問修飾符,也不接受任何參數(shù);??

無論創(chuàng)建多少類型的對象,靜態(tài)構造函數(shù)只執(zhí)行一次;??

運行庫創(chuàng)建類實例或者首次訪問靜態(tài)成員之前,運行庫調(diào)用靜態(tài)構造函數(shù);??

靜態(tài)構造函數(shù)執(zhí)行先于任何實例級別的構造函數(shù);??

顯然也就無法使用this 和 base 來調(diào)用構造函數(shù)。

?著作權歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

友情鏈接更多精彩內(nèi)容