में दी गई तो हम करने के लिए देखने के लिए विशेष प्रकार के साथ संगत है स्कैला कंपाइलर, स्रोत हमें समझने में मदद कर सकते हैं कि समस्या क्या है। मैंने कभी स्कैला कंपाइलर में योगदान नहीं दिया है, लेकिन मैंने स्रोतों को बहुत पठनीय पाया है और मैंने पहले ही इसकी जांच की है।
टाइप अनुमान के लिए जिम्मेदार वर्ग scala.tools.nsctypechecker.Infer
है जो आप अपनी त्रुटि के एक भाग के लिए स्कैला कंपाइलर स्रोतों को देखकर आसानी से पा सकते हैं। आप बाहर निम्नलिखित टुकड़ा मिल जाएगा:
/** error if arguments not within bounds. */
def checkBounds(pos: Position, pre: Type, owner: Symbol,
tparams: List[Symbol], targs: List[Type], prefix: String) = {
//@M validate variances & bounds of targs wrt variances & bounds of tparams
//@M TODO: better place to check this?
//@M TODO: errors for getters & setters are reported separately
val kindErrors = checkKindBounds(tparams, targs, pre, owner)
if(!kindErrors.isEmpty) {
error(pos,
prefix + "kinds of the type arguments " + targs.mkString("(", ",", ")") +
" do not conform to the expected kinds of the type parameters "+ tparams.mkString("(", ",", ")") + tparams.head.locationString+ "." +
kindErrors.toList.mkString("\n", ", ", ""))
}
क्यों checkKindBounds(tparams, targs, pre, owner)
उन त्रुटियों को देता है तो अब बात समझ रहा है।
: आप नीचे विधि कॉल श्रृंखला जाना, तो आप उस checkKindBounds एक और तरीका
val errors = checkKindBounds0(tparams, targs, pre, owner, true)
आप समस्या, उच्च kinded प्रकार की सीमा से जाँच से जुड़ा है लाइन 5784 पर, checkKindBoundsHK अंदर देखेंगे फोन देखेंगे
if (!sameLength(hkargs, hkparams)) {
if (arg == AnyClass || arg == NothingClass) (Nil, Nil, Nil) // Any and Nothing are kind-overloaded
else {error = true; (List((arg, param)), Nil, Nil) } // shortcut: always set error, whether explainTypesOrNot
}
परीक्षा उत्तीर्ण की नहीं है, ऐसा लगता है कि मेरी डीबगर में:
hkargs$1 = {[email protected]}"List()"
arg$1 = {[email protected]}"class List"
param$1 = {[email protected]}"type B"
paramowner$1 = {[email protected]}"method process"
underHKParams$1 = {[email protected]}"List(type R)"
withHKArgs$1 = {[email protected]}"List()"
exceptionResult12 = null
hkparams$1 = {[email protected]}"List(type R)"
तो ऐसा लगता है एक उच्च kinded परम, प्रकार आर वहाँ है, लेकिन वहाँ कोई प्रदान करना है की तरह इसके लिए डी मान।
आप वास्तव में checkKindBounds करने के लिए वापस जाओ, तो आप देखते हैं कि स्निपेट के बाद:
val (arityMismatches, varianceMismatches, stricterBounds) = (
// NOTE: *not* targ.typeSymbol, which normalizes
checkKindBoundsHK(tparamsHO, targ.typeSymbolDirect, tparam, tparam.owner, tparam.typeParams, tparamsHO)
)
arityMismatches
एक टपल सूची, बी में शामिल है और अब आप यह भी देख सकते त्रुटि संदेश गलत है: प्रकार तर्कों की
अनुमानित प्रकार (MyFoo, MyFoo, सूची [X]) प्रकार पैरामीटर (प्रकार एफ, प्रकार आर, ग्रुप बी) की उम्मीद प्रकार के अनुरूप नहीं है। सूची [एक्स] के प्रकार पैरामीटर ग्रुप बी की उम्मीद मापदंडों मेल नहीं खाते: कक्षा सूची एक प्रकार पैरामीटर है, लेकिन ग्रुप बी शून्य
है वास्तव में अगर आप निम्न पर लाइन 5859 पर एक ब्रेकपाइंट डाल फोन
checkKindBoundsHK(tparamsHO, targ.typeSymbolDirect, tparam, tparam.owner, tparam.typeParams, tparamsHO)
आप देख सकते हैं कि
tparam = {[email protected]}"type B"
targ = {[email protected]}"List[X]"
निष्कर्ष:
किसी कारण से, जटिल उच्च प्रकार के प्रकार जैसे आपके जैसे व्यवहार से निपटने पर, स्कैला कंपाइलर अनुमान सीमित है। मुझे नहीं पता कि यह कहां से आता है, शायद आप कंपाइलर टीम
पर एक बग भेजना चाहते हैं। मैं स्कैला का उपयोग कर रहा हूं 2.9.3-20120917-121530-db16547873 –