5.2.15 · D5 · HinglishC++ Programming

Question bankTemplate specialization — full and partial

1,861 words8 min read↑ Read in English

5.2.15 · D5 · Coding › C++ Programming › Template specialization — full and partial


True or false — justify

A full specialization must begin with template<>.
True — ek full specialization mein zero free parameters hote hain, isliye template ke baad angle brackets khali hote hain; inhe chhod dene par compiler isse primary ki redeclaration samajh leta hai.
A partial specialization can leave template<...> (that is, a non‑empty comma‑separated parameter list) present.
True — partial matlab kuch parameters free rehte hain, to woh free names usi list mein rehte hain (jaise template<class T> struct Box<T*>).
Function templates can be partially specialized just like class templates.
False — function templates sirf full specialization support karte hain; partial-jaisi behaviour ke liye overloading use karte hain (functions mein se best match choose karke), kyunki overload resolution already woh kaam karta hai.
For int*, the partial T* is more specialized than the primary T.
True — har woh type jo T* se match karti hai (saare pointers) T se bhi match karti hai, lekin ulta nahi, isliye T* ek strict subset describe karta hai aur partial ordering se jeet jaata hai.
If two partial specializations both match a type, the compiler picks the one written first in the file.
False — declaration order irrelevant hai; compiler most specialized wali pick karta hai, aur agar dono mein se koi bhi doosre se zyada specialized nahi hai to ambiguity error report karta hai.
A specialization may be placed in any namespace as long as the name matches.
False — specialization ko primary template ke same namespace mein rehna chahiye, warna woh ek alag, unrelated template ban jaati hai.
std::vector<bool> is just std::vector<T> with T = bool.
False — yeh ek special container specialization hai jo booleans ko bit-pack karti hai, isliye yeh real bool objects store nahi karti aur element access par alag behave bhi karti hai. Yeh bit-packing hi woh kaaran hai jiske liye std::vector<bool> special case ek documented gotcha ke roop mein exist karta hai.
A partial specialization can introduce a new default template argument.
False — default template arguments sirf primary template par hote hain; ek partial spec unhe use to kar sakti hai lekin naye declare nahi kar sakti.
You may specialize a template after the compiler has already instantiated it for that type.
False — specialization pehle use se pehle visible honi chahiye; baad mein specialize karna ill-formed hai (aksar koi diagnostic required nahi hoti, jo ise dangerous banata hai).
constexpr if can replace some uses of specialization.
True — ek template body ke andar, constexpr if alag specialization structs likhe bina compile-time condition ke hisaab se alag code paths select kar sakta hai.

Spot the error

template<class T> struct Box { };
struct Box<int> { };   // full spec for int?
What is wrong?
Full specialization mein template<> missing hai; iske bina yeh line ek non-template struct Box<int> ki redefinition lagti hai aur specialization ke roop mein compile nahi hogi.
template<class T> T maxi(T a, T b);
template<class T> T maxi<T*>(T* a, T* b);  // "partial spec" for pointers
What is wrong?
Function templates ko partially specialize nahi kiya ja sakta, isliye maxi<T*> illegal hai; iske bajay ek alag maxi(T* a, T* b) overload likho.
namespace lib { template<class T> struct H { }; }
template<> struct lib::H<int> { };  // at global scope
Is this correct?
Yeh form full specializations ke liye actually allowed hai agar qualified name ke saath likha jaaye — lekin ek common error hai koi alag namespace open karna ya lib:: qualifier bhool jaana, jo lib::H ki specialization ki jagah ek alag template produce karta hai.
template<class A,class B> struct M { };
template<class A> struct M<A,int> { };
template<class B> struct M<int,B> { };
M<int,int> m;
Why won't this compile?
Dono partials M<int,int> se match karti hain aur dono mein se koi bhi doosre se zyada specialized nahi hai, isliye compiler choose nahi kar sakta aur ambiguity error report karta hai.
template<class T = int> struct P { };
template<class T = char> struct P<T*> { };  // new default in partial
What rule is broken?
Ek partial specialization koi naya default template argument (= char) introduce nahi kar sakti; defaults sirf primary par allowed hain.
template<class T> struct Trait { static const bool ptr = false; };
Trait<int*> a;
template<class T> struct Trait<T*> { static const bool ptr = true; };
What is subtly wrong?
Partial Trait<T*> Trait<int*> ke already instantiate hone के baad declare ki gayi hai; specialization us pehle use se pehle appear karni chahiye warna program ill-formed hai.

Why questions

Why do classes get partial specialization but functions do not?
Classes mein koi overloading mechanism nahi hai, isliye unhe type shape ke hisaab se behaviour vary karne ke liye partial specialization chahiye; functions already overload resolution se "best match" resolve karte hain, isliye two competing rules se bachne ke liye partial functions ke liye chhod diya gaya.
Why must a full specialization write the type in <...> after the name but empty <> before it?
Khali template<> announce karta hai "koi parameter fill karna baaki nahi," jabki Box<int> batata hai ki tum primary ki kaun si instantiation replace kar rahe ho — do brackets alag-alag sawalon ka jawab dete hain.
Why is T* considered "more specialized" than T?
Kyunki T* se match hone wale types (pointers) ka set T se match hone wale types (sab kuch) ka strict subset hai; ek narrow pattern zyada clear intent signal karta hai, isliye partial ordering ise unconstrained primary se upar rank karta hai.
Why does specialization keep the same name and interface instead of a new function?
Taaki caller ka code kabhi change na ho — special case sirf implementation swap karta hai, compiler ko transparently sahi type ko sahi recipe tak route karne deta hai, aur isi tarah type traits apni machinery chhupate hain.
Why is std::is_pointer typically built with a partial specialization?
Primary value = false set karta hai, aur partial is_pointer<T*> value = true set karta hai, isliye pointer ki shape match karna exactly wahi hai jo pointer types ko distinguish karta hai — yeh partial specialization ka canonical use hai.
Why does specialization matter more for performance than for correctness sometimes?
Ek generic recipe sahi lekin slow ya wasteful ho sakti hai (jaise booleans ke liye puri bytes store karna); std::vector<bool> jaisi specialization same interface ke liye ek tighter representation swap kar leti hai.

Edge cases

First, the mini-template these edge cases refer to:

template<class A, class B> struct Pair2 { static const char* k(){ return "AB"; } };
template<class B>          struct Pair2<int, B> { static const char* k(){ return "intB"; } };
If a type matches only the primary template and no specialization, what happens?
Woh primary template use karta hai — primary hamesha un sabke liye fallback hota hai jo kisi specialization se match nahi karte.
If both a full and a partial specialization match a type, which wins?
Full specialization hamesha jeetti hai, kyunki saare parameters ko concrete types se fix karna sabse specific possible match hai aur kisi bhi partial ko beat karta hai.
Using the Pair2 above, what happens when you instantiate Pair2<int, char>?
Partial Pair2<int, B> B = char ke saath fire hoti hai kyunki pehla parameter int par pinned hai jabki B free rehta hai — sirf kuch parameters fixed hain, jo partial ki definition hai.
Can you specialize a template for const int separately from int?
Haan — const int aur int alag types hain, isliye Trait<const int> aur Trait<int> independent specializations hain jo collide nahi karengi.
What does the primary template do if it is only declared but never defined, and every real type is specialized?
Yeh tab tak theek compile hota hai jab tak koi unspecialized type kabhi instantiate na ho — undefined primary "compile error trap" ki tarah kaam karta hai us type ke liye jo tum handle karna bhool gaye.
Does a partial specialization of a class template for T& (reference) work the same as for T*?
Haan — tum reference shape ko bilkul pointer shape ki tarah match kar sakte ho, aur partial ordering T& ko T ka strict subset exactly usi tarah treat karta hai.
If two overloads and a specialization could all apply to a function call, what resolves first?
Overload resolution pehle function templates aur non-templates mein se choose karta hai; ek full specialization ek independent candidate ke roop mein participate nahi karti — yeh sirf woh body define karti hai jo primary template select ho jaane ke baad choose ki jaati hai. Candidates ke beech finer control ke liye dekho Tag Dispatch and Policy-based Design.

Recall Ek-line self-test

Upar ke saare answers cover karo; agar tumhari justification reason name karti hai (subset, same-namespace, before-use, no-partial-functions) aur sirf "true/false" nahi, to concept tumhara hai.