版權(quán)說(shuō)明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)
文檔簡(jiǎn)介
1、C+newnew 是C+的一個(gè)關(guān)鍵字,同時(shí)也是操作符關(guān)于new 的話題格外多,由于它確實(shí)比較簡(jiǎn)單,也格外奇特,下面我將把我了解到的與new有關(guān)的內(nèi)容做一個(gè)總結(jié)new 的過(guò)程當(dāng)我們使用關(guān)鍵字new 在堆上動(dòng)態(tài)創(chuàng)立一個(gè)對(duì)象時(shí),它實(shí)際上做了三件事:獲得一塊內(nèi)存空間調(diào)用構(gòu)造函數(shù)返回正確的指針固然,假設(shè)我們創(chuàng)立的是簡(jiǎn)潔類型的變量,那么第 二步會(huì)被省略假設(shè)我們定義了如下一個(gè)類A:class Ainti;public:A(int _i) :i(_i*_i) void Say printf(“i=%dn“, i); ;A* pa = new A(3);那么上述動(dòng)態(tài)創(chuàng)立一個(gè)對(duì)象的過(guò)程大致相當(dāng)于以下三句話只是大致
2、上:雖然從效果上看,這三句話也得到了一個(gè)有效的指向堆上的A 對(duì)象的指針pa,但區(qū)分在于,當(dāng)malloc 失敗時(shí),它不會(huì)調(diào)用安排內(nèi)存失敗處理程序new_handler,而使用new 的話會(huì)的因此我們還是要盡可能的使用new,除非有一些特別的需求new的三種形態(tài)到目前為止,本文所提到的new 都是指的new operator 或稱為new expression,但事實(shí)上在C+中一提到new,至少可能代表以下三種含義:new operatoroperator newplacement newnew operator 就是我們尋常所使用的new,其行為就是前面所說(shuō)的三個(gè)步驟,我們不能更改它但具體到某一
3、步驟中的行為,假設(shè)它不滿足我們的具體要求時(shí),我們是有可能更改它的三個(gè)步驟中最終一步只是簡(jiǎn)潔的做一個(gè)指針的類型轉(zhuǎn)換,沒(méi)什么可說(shuō)的,并且在編譯出的代碼中也并不需要這種轉(zhuǎn)換,只是人為的生疏罷了但前兩步就有些內(nèi)容了new operator 的第一步安排內(nèi)存實(shí)際上是通過(guò)調(diào)用operator new 來(lái)完成的,這里的new 實(shí)際上是像加減乘除一樣的操作符,因此也是可以重載的operator new 默認(rèn)狀況下首先調(diào)用安排內(nèi)存的代碼,嘗試得到一段堆上的空間,假設(shè)成功就返回,假設(shè)失敗,則轉(zhuǎn)而 去調(diào)用一個(gè)new_hander,然后連續(xù)重復(fù)前面過(guò)程假設(shè)我們對(duì)這個(gè)過(guò)程不滿足,就可以重 operator new,來(lái)設(shè)
4、置我們期望的行為例如:class Apublic:void* operator new(size_t size)printf(“operator new calledn“);return :operator new(size);A* a = new A;這里通過(guò):operator new調(diào)用了原有的全局的new,實(shí)現(xiàn)了在安排內(nèi)存之前輸出一句話全局的operator new 也是可以重載的,但這樣一來(lái)就不能再遞歸的使用new 來(lái)安排內(nèi)存,而只能使用malloc 了:void* operator new(size_t size)printf(“global newn“);return malloc
5、(size);相應(yīng)的,delete 也有delete operator 和 operator delete 之分,后者也是可以重載的并且,假設(shè)重載了operator new,就應(yīng)當(dāng)也相應(yīng)的重載operator delete,這是良好的編程習(xí)慣new的第三種形態(tài)placement new是用來(lái)實(shí)現(xiàn)定位構(gòu)造的,因此可以實(shí)現(xiàn)new operator 三步操作中的其次步,也就是在取得了一塊可以容納指定類型對(duì)象的內(nèi)存后,在這塊內(nèi)存上構(gòu)造一個(gè)對(duì)象,這有點(diǎn)類似于前面代碼中的p-A:A(3);這句話,但這并不是一 個(gè)標(biāo)準(zhǔn)的寫法,正確的寫法是使用placement new:#include void mainc
6、har ssizeof(A);A* p = (A*)s;new(p) A(3); /p-A:A(3);p-Say;placement new這里new(p) A(3)placement new 了,它實(shí)現(xiàn)了在指定內(nèi)存地址上用指定類型的構(gòu)造函數(shù)來(lái)構(gòu)造一個(gè)對(duì)象的功能,后面A(3)就是對(duì)構(gòu)造函數(shù)的顯式調(diào)用這里不難覺察,這塊指定的地址既可以是棧,又可以是堆,placement 對(duì)此不加區(qū)分但是,除非特別必要,不要直接使用placement new ,這到底不是用來(lái)構(gòu)造對(duì)象的正式寫法,只不過(guò)是new operator 的一個(gè)步驟而已使用new operator 地編譯器會(huì)自動(dòng)生成對(duì)placement n
7、ew 的調(diào)用的代碼,因此也會(huì)相應(yīng)的生成使用delete 時(shí)調(diào)用析構(gòu)函數(shù)的代碼假設(shè)是像上面那樣在棧上使用了placement new,則必需手工調(diào)用析構(gòu)函數(shù),這也是顯式調(diào)用析構(gòu)函數(shù)的唯一狀況:p-A;當(dāng)我們覺得默認(rèn)的new operator 對(duì)內(nèi)存的治理不能滿足我們的需要,而期望自己手工的治理內(nèi)存時(shí),placement new就有用了STL allocator就使用了這種方式,借助placement new來(lái)實(shí)現(xiàn)更機(jī)敏有效的內(nèi)存治理處理內(nèi)存安排特別正如前面所說(shuō),operator new 的默認(rèn)行為是懇求安排內(nèi)存,假設(shè)成功則返回此內(nèi)存地址,假設(shè)失敗則調(diào)用一個(gè)new_handler,然后再重復(fù)此過(guò)程
8、于是,想要從operator new 的執(zhí)行過(guò)程中返回,則必定需要滿足以下條件之一:于是,我們可以假設(shè)默認(rèn)狀況下operator new 的行為是這樣的:void* operator new(size_t size)void* p = nullwhile(!(p=malloc(size)if(null = new_handler)throwbad_alloc;trynew_handler;catch(bad_alloce)throw e;catchreturn p;在默認(rèn)狀況下,new_handler 的行為是拋出一個(gè)bad_alloc 特別,因此上述循環(huán)只會(huì)執(zhí)行一次但假設(shè)我們不期望使用默認(rèn)行
9、為,可以自定義一個(gè)new_handler,并使用std:set_new_handler函數(shù)使其生效在自定義的new_handler中,我們可以拋出特別,可以完畢程序,也可以運(yùn)行一些代碼使得有可能有內(nèi)存被空閑出來(lái),從而下一次安排時(shí)或許會(huì)成功,也可以通過(guò)set_new_handler來(lái)安裝另一個(gè)可能更有效的new_handler例如: void MyNewHandlerprintf(New handler called!n);throw std:bad_alloc;std:set_new_handler(MyNewHandler);這里 new_handler 程序在拋出特別之前會(huì)輸出一句話應(yīng)當(dāng)留
10、意,在new_handler 的代碼里應(yīng)當(dāng)留意避開再嵌套有對(duì)new 的調(diào)用,由于假設(shè)這里調(diào)用new 再失敗的話,可能會(huì)再導(dǎo)致對(duì)new_handler的調(diào)用,從而導(dǎo)致無(wú)限遞歸調(diào)用這是我猜的,并沒(méi)有嘗試過(guò)在編程時(shí)我們應(yīng)當(dāng)留意到對(duì)new 的調(diào)用是有可能有特別被拋出的,因此在new 的代碼四周應(yīng)當(dāng)留意保持其事務(wù)性,即不能由于調(diào)用new 失敗拋出特別來(lái)導(dǎo)致不正確的程序規(guī)律或數(shù)據(jù)構(gòu)造的消滅例如:class SomeClassstatic int count;SomeClass public:static SomeClass* GetNewInstancecount+;return new SomeClas
11、s;靜態(tài)變量count 用于記錄此類型生成的實(shí)例的個(gè)數(shù),在上述代碼中,假設(shè)因new 安排內(nèi)存失敗而拋出特別,那么其實(shí)例個(gè)數(shù)并沒(méi)有增加,但count 變量的值卻已經(jīng)多了一個(gè),從而數(shù)據(jù)構(gòu)造被破壞正確的寫法是:static SomeClass* GetNewInstanceSomeClass* p = new SomeClass;count+;return p;這樣一來(lái),假設(shè)new 失敗則直接拋出特別,count 的值不會(huì)增加類似的,在處理線程同步時(shí),也要留意類似的問(wèn)題:void SomeFunc/加一個(gè)鎖delete p;p = new SomeClass;unlock(someMutex);ST
12、L 的內(nèi)存安排與traits 技巧STL 原碼剖析一書中具體分析了SGI STL 的內(nèi)存安排器的行為與直接使用new operator 不同的是,SGI STL 并不依靠C+默認(rèn)的內(nèi)存安排方式,而是使用一套自行實(shí)現(xiàn)的方案首先SGI STL 將可用內(nèi)存整塊的安排,使之成為當(dāng)前進(jìn)程可用的內(nèi)存,當(dāng)程序中確實(shí)需要安排內(nèi)存時(shí),先從這些已懇求好的大內(nèi)存塊中嘗試取得內(nèi)存,假設(shè)失敗的話再嘗試 整塊的安排大內(nèi)存這種做法有效的避開了大量?jī)?nèi)存碎片的消滅,提高了內(nèi)存治理效率為了實(shí)現(xiàn)這種方式,STL使用了placementnew,通過(guò)在自己治理的內(nèi)存空間上使用placement new來(lái)構(gòu)造對(duì)象,以到達(dá)原有new op
13、erator所具有的功能templateinline void construct(T1* p, const T2& value)此函數(shù)接收一個(gè)已構(gòu)造的對(duì)象,通過(guò)拷貝構(gòu)造的方式在給定的內(nèi)存地址p 上構(gòu)造一個(gè)對(duì)象,代碼中后半截T1(value)便是placement new 語(yǔ)法中調(diào)用構(gòu)造函數(shù)的寫法,假設(shè)傳入的對(duì)象value 正是所要求的類型T1,那么這里就相當(dāng)于調(diào)用拷貝構(gòu)造函數(shù)類似的,因使用placement new,編譯器不會(huì)自動(dòng)產(chǎn)生調(diào)用析構(gòu)函數(shù)的代碼,需要手工的實(shí)現(xiàn): template inline void destory(T* pointer)與此同時(shí),STL中還有一個(gè)接收兩個(gè)迭代器的
14、destory版本,可將某容器上指定范圍內(nèi) 的對(duì)象全部銷毀典型的實(shí)現(xiàn)方式就是通過(guò)一個(gè)循環(huán)來(lái)對(duì)此范圍內(nèi)的對(duì)象逐一調(diào)用析構(gòu)函數(shù) 假設(shè)所傳入的對(duì)象是非簡(jiǎn)潔類型,這樣做是必要的,但假設(shè)傳入的是簡(jiǎn)潔類型,或者根本 沒(méi)有必要調(diào)用析構(gòu)函數(shù)的自定義類型例如只包含數(shù)個(gè)int 成員的構(gòu)造體,那么再逐一調(diào)用析構(gòu)函數(shù)是沒(méi)有必要的,也鋪張了時(shí)間為此,STL 使用了一種稱為type traits的技巧,在編譯器就推斷出所傳入的類型是否需要調(diào)用析構(gòu)函數(shù):template inline void destory(ForwardIterator first, ForwardIterator last) destory(firs
15、t,last,value_type(first);其中 value_type用于取出迭代器所指向的對(duì)象的類型信息,于是:templateinline voiddestory(ForwardIterator first, ForwardIterator last, T*)typedeftypenametype_traits:has_trivial_destructortrivial_destructor; destory_aux(first,last,trivial_destructor);/假設(shè)需要調(diào)用析構(gòu)函數(shù): templateinlinevoiddestory_aux(ForwardIte
16、ratorfirst,ForwardIteratorlast,false_type)for(; first last; +first)destory(&*first); /first 是迭代器,*first 取出其真正內(nèi)容,然后再用&取地址/假設(shè)不需要,就什么也不做: tempalteinlinevoiddestory_aux(ForwardIteratorfirst,ForwardIteratorlast,true_type)因上述函數(shù)全都是inline 的,所以多層的函數(shù)調(diào)用并不會(huì)對(duì)性能造成影響,最終編譯的結(jié)果依據(jù)具體的類型就只是一個(gè)for循環(huán)或者什么都沒(méi)有這里的關(guān)鍵在于 type_tra
17、its這個(gè)模板類上,它依據(jù)不同的T 類型定義出不同的has_trivial_destructor的結(jié)果,假設(shè)T 是簡(jiǎn)潔類型,就定義為true_type 類型,否則就定義為false_type 類型其中true_typefalse_type 只不過(guò)是兩個(gè)沒(méi)有任何內(nèi)容的類,對(duì)程序的執(zhí)行結(jié)果沒(méi)有什么意義,但在編譯器看來(lái)它對(duì)模板如何特化就具有格外重要的指導(dǎo)意義了,正如上面代碼 所示的那樣type_traits也是特化了的一系列模板類:structtrue_type ; structfalse_type ;template structtype_traitspublic:typedeffalse _ty
18、pe has_trivial_destructor;template/模板特化structtype_traits/int 的特化版本public:typedeftrue_type has_trivial_destructor;/其他簡(jiǎn)潔類型的特化版本假設(shè)要把一個(gè)自定義的類型MyClass 也定義為不調(diào)用析構(gòu)函數(shù),只需要相應(yīng)的定義 type_traits的一個(gè)特化版本即可:templatestructtype_traitspublic:typedeftrue_type has_trivial_destructor;模板是比較高級(jí)的C+編程技巧,模板特化模板偏特化就更是技巧性很強(qiáng)的東西,STL 中
19、的type_traits 充分借助模板特化的功能,實(shí)現(xiàn)了在程序編譯期通過(guò)編譯器來(lái)打算為每一處調(diào)用使用哪個(gè)特化版本,于是在不增加編程簡(jiǎn)單性的前提下大大提高了程序的運(yùn)行效率更具體的內(nèi)容可參考STL源碼剖析其次三章中的相關(guān)內(nèi)容帶有new 和delete我們經(jīng)常會(huì)通過(guò)new 來(lái)動(dòng)態(tài)創(chuàng)立一個(gè)數(shù)組,例如:嚴(yán)格的說(shuō),上述代碼是不正確的,由于我們?cè)诎才艃?nèi)存時(shí)使用的是new,而并不是簡(jiǎn)潔new,但釋放內(nèi)存時(shí)卻用的是delete 正確的寫法是使用delete:deletes;但是,上述錯(cuò)誤的代碼好似也能編譯執(zhí)行,并不會(huì)帶來(lái)什么錯(cuò)誤事實(shí)上,new 與newdelete 與 delete是有區(qū)分的,特別是當(dāng)用來(lái)操作簡(jiǎn)
20、單類型時(shí)假設(shè)針對(duì)一個(gè)我們自定義的類MyClass使用new:MyClass*p=newMyClass10;上述代碼的結(jié)果是在堆上安排了10 個(gè)連續(xù)的MyClass實(shí)例,并且已經(jīng)對(duì)它們依次調(diào)用了構(gòu)造函數(shù),于是我們得到了10 個(gè)可用的對(duì)象,這一點(diǎn)與JavaC#有區(qū)分的,JavaC#中這樣的結(jié)果只是得到了10 個(gè)null 換句話說(shuō),使用這種寫法時(shí)MyClass 必需擁有不帶參數(shù)的構(gòu)造函數(shù),否則會(huì)覺察編譯期錯(cuò)誤,由于編譯器無(wú)法調(diào)用有參數(shù)的構(gòu)造函數(shù)當(dāng)這樣構(gòu)造成功后,我們可以再將其釋放,釋放時(shí)使用delete:deletep;當(dāng)我們對(duì)動(dòng)態(tài)安排的數(shù)組調(diào)用delete時(shí),其行為依據(jù)所申請(qǐng)的變量類型會(huì)有所不同假
21、設(shè) p 指向簡(jiǎn)潔類型,如intchar 等,其結(jié)果只不過(guò)是這塊內(nèi)存被回收,此時(shí)使用delete與delete 沒(méi)有區(qū)分,但假設(shè)p 指向的是簡(jiǎn)單類型,delete會(huì)針對(duì)動(dòng)態(tài)安排得到的每個(gè)對(duì)象調(diào)用析構(gòu)函數(shù),然后再釋放內(nèi)存因此,假設(shè)我們對(duì)上述安排得到的p 指針直接使用delete 來(lái)回收,雖然編譯期不報(bào)什么錯(cuò)誤由于編譯器根本看不出來(lái)這個(gè)指針p 是如何安排的, 但在運(yùn)行時(shí)DEBUG 狀況下會(huì)給出一個(gè)Debug assertion failed提示到這里,我們很簡(jiǎn)潔提出一個(gè)問(wèn)題delete是如何知道要為多少個(gè)對(duì)象調(diào)用析構(gòu)函數(shù)的?要答復(fù)這個(gè)問(wèn)題,我們可以首先看一看new的重載class MyClasspu
22、blic:MyClassprintf(“ctorn“);MyClassprintf(“dtorn“);void*operatornew(size_tsize)void*p=operatornew(size);printf(“calling new with size=%d address=%pn“, size, p);return p;/ 主函數(shù)MyClass* mc = new MyClass3; printf(“addressofmc=%pn“,mc);deletemc;運(yùn)行此段代碼,得到的結(jié)果為:VC2022ctorctorctordtordtordtor雖然對(duì)構(gòu)造函數(shù)和析構(gòu)函數(shù)的調(diào)用結(jié)
23、果都在預(yù)料之中,但所申請(qǐng)的內(nèi)存空間大小以及 地址的數(shù)值卻消滅了問(wèn)題我們的類MyClass 4 個(gè)字節(jié),并且申請(qǐng)的數(shù)組中有3 個(gè)元素,那么應(yīng)當(dāng)一共申請(qǐng)12 個(gè)字節(jié)才對(duì),但事實(shí)上系統(tǒng)卻為我們申請(qǐng)了16 字節(jié),并且在operator new返后我們得到的內(nèi)存地址是實(shí)際申請(qǐng)得到的內(nèi)存地址值加4 的結(jié)果也就是說(shuō),當(dāng)為簡(jiǎn)單類型動(dòng)態(tài)安排數(shù)組時(shí),系統(tǒng)自動(dòng)在最終得到的內(nèi)存地址前空出了4 個(gè)字節(jié), 4 個(gè)字節(jié)的內(nèi)容與動(dòng)態(tài)安排數(shù)組的長(zhǎng)度有關(guān)通過(guò)單步跟蹤,很簡(jiǎn)潔覺察4 個(gè)字節(jié)對(duì)應(yīng)的int 0 x00000003,也就是說(shuō)記錄的是我們安排的對(duì)象的個(gè)數(shù)轉(zhuǎn)變一newoperator的行為相當(dāng)于下面的偽代碼:template
24、 T*New(intcount)int size = sizeof(T) * count + 4; void*p=T:operatornew(size);*(int*)p=count;T* pt = (T*)(int)p + 4); for(inti=0;icount;i+)new(&pti) T;returnpt;上述示意性的代碼省略了特別處理的局部,只是呈現(xiàn)當(dāng)我們對(duì)一個(gè)簡(jiǎn)單類型使用new來(lái)動(dòng)態(tài)安排數(shù)組時(shí)其真正的行為是什么,從中可以看到它安排了比預(yù)期多4 個(gè)字節(jié)的內(nèi)存并用它來(lái)保存對(duì)象的個(gè)數(shù),然后對(duì)于后面每一塊空間使用placement new 來(lái)調(diào)用無(wú)參構(gòu)造函數(shù),這也就解釋了為什么這種狀況下
25、類必需有無(wú)參構(gòu)造函數(shù),最終再將首地址返回類似的,我們很簡(jiǎn)潔寫出相應(yīng)的delete的實(shí)現(xiàn)代碼:template void Delete(T* pt)int count = (int*)pt)-1; for(inti=0;icount;i+)pti.T;void* p = (void*)(int)pt 4);T:operatordelete(p);由此可見,在默認(rèn)狀況下operator new與operator new 的行為是一樣的,operatordeleteoperator delete 也是,不同的是new operator new operatordelete operatordelet
26、e operator 固然,我們可以依據(jù)不同的需要來(lái)選擇重載帶有和不帶有的 operatornew和delete,以滿足不同的具體需求把前面類MyClass 的代碼稍做修改注釋掉析構(gòu)函數(shù),然后再來(lái)看看程序的輸出:callingnewwithsize=12address=003A5A58ctorctorctoraddress of mc=003A5A58這一次,new老狡猾實(shí)的申請(qǐng)了 12 個(gè)字節(jié)的內(nèi)存,并且申請(qǐng)的結(jié)果與new operator返回的結(jié)果也是一樣的,看來(lái),是否在前面添加4 個(gè)字節(jié),只取決于這個(gè)類有沒(méi)有析構(gòu)函數(shù),固然,這么說(shuō)并不準(zhǔn)確,正確的說(shuō)法是這個(gè)類是否需要調(diào)用構(gòu)造函數(shù),由于如下
27、兩種 狀況下雖然這個(gè)類沒(méi)聲明析構(gòu)函數(shù),但還是多申請(qǐng)了4 個(gè)字節(jié):一是這個(gè)類中擁有需要調(diào)用析構(gòu)函數(shù)的成員,二是這個(gè)類繼承自需要調(diào)用析構(gòu)函數(shù)的類于是,我們可以遞歸的定義 需要調(diào)用析構(gòu)函數(shù)的類為以下三種狀況之一:顯式的聲明白析構(gòu)函數(shù)的擁有需要調(diào)用析構(gòu)函數(shù)的類的成員的繼承自需要調(diào)用析構(gòu)函數(shù)的類的類似的,動(dòng)態(tài)申請(qǐng)簡(jiǎn)潔類型的數(shù)組時(shí),也不會(huì)多申請(qǐng)4 個(gè)字節(jié)于是在這兩種狀況下, 釋放內(nèi)存時(shí)使用delete 或delete都可以,但為養(yǎng)成良好的習(xí)慣,我們還是應(yīng)當(dāng)留意只要是動(dòng)態(tài)安排的數(shù)組,釋放時(shí)就使用delete釋放內(nèi)存時(shí)如何知道長(zhǎng)度但這同時(shí)又帶來(lái)了問(wèn)題,既然申請(qǐng)無(wú)需調(diào)用析構(gòu)函數(shù)的類或簡(jiǎn)潔類型的數(shù)組時(shí)并沒(méi) 有記錄
28、個(gè)數(shù)信息,那么operator delete,或更直接的說(shuō) free是如何來(lái)回收這塊內(nèi)存的呢?這就要爭(zhēng)辯malloc返回的內(nèi)存的構(gòu)造了與new類似的是,實(shí)際上在malloc申請(qǐng)內(nèi)存時(shí) 也多申請(qǐng)了數(shù)個(gè)字節(jié)的內(nèi)容,只不過(guò)這與所申請(qǐng)的變量的類型沒(méi)有任何關(guān)系,我們從調(diào)用malloc 時(shí)所傳入的參數(shù)也可以理解這一點(diǎn)它只接收了要申請(qǐng)的內(nèi)存的長(zhǎng)度,并不關(guān)系這塊內(nèi)存用來(lái)保存什么類型下面運(yùn)行這樣一段代碼做個(gè)試驗(yàn):char*p=0;for(inti = 0; i 40; i +=4)char*s=newchari;printf(“alloc%2dbytes,address=%pdistance=%dn“,i,s,s-p);我們直接來(lái)看VC2022 下Release 版本
溫馨提示
- 1. 本站所有資源如無(wú)特殊說(shuō)明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁(yè)內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒(méi)有圖紙預(yù)覽就沒(méi)有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫(kù)網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。
最新文檔
- 福建師范大學(xué)《社會(huì)學(xué)概論》2021-2022學(xué)年第一學(xué)期期末試卷
- 福建師范大學(xué)《環(huán)境生態(tài)工程》2021-2022學(xué)年第一學(xué)期期末試卷
- 福建師范大學(xué)《地理語(yǔ)言學(xué)》2023-2024學(xué)年第一學(xué)期期末試卷
- 第14章 因子分析1統(tǒng)計(jì)學(xué)原理課件
- 中國(guó)高血壓防治指南關(guān)于高血壓急癥的解讀
- 深度報(bào)文檢測(cè)技術(shù)Comware V7 DPI
- 油田動(dòng)土作業(yè)安全管理實(shí)施細(xì)則
- 教研活動(dòng)記錄(班級(jí)環(huán)創(chuàng)及擺布)
- 2024年太原客運(yùn)駕駛員考試試題答案解析
- 2024年防城港A1客運(yùn)從業(yè)資格證
- 《語(yǔ)文青蛙看?!穚pt課件
- 河湖生態(tài)系統(tǒng)保護(hù)與修復(fù)工程技術(shù)導(dǎo)則 SLT800-2020_(高清-有效)
- 愛護(hù)我們的牙齒PPT
- 日語(yǔ)名大全(附帶中文和英語(yǔ)翻譯)
- 2022年小學(xué)數(shù)學(xué)因數(shù)與倍數(shù)、質(zhì)數(shù)與合數(shù)練習(xí)題答案2
- 超星爾雅學(xué)習(xí)通《就業(yè)指導(dǎo)》章節(jié)測(cè)試答案
- 月度會(huì)議ppt模板
- 成都銀花絲首飾消費(fèi)特征分析
- 社區(qū)衛(wèi)生服務(wù)中心安全生產(chǎn)自查表
- 不“管資產(chǎn)”,如何“管資本”
- 【案例】萬(wàn)福生科財(cái)務(wù)造假案例分析
評(píng)論
0/150
提交評(píng)論