public ALittleScriptMethodReturnTailDecElement GetMethodReturnTailDec() { if (m_flag_MethodReturnTailDec) { return(m_cache_MethodReturnTailDec); } m_flag_MethodReturnTailDec = true; foreach (var child in m_childs) { if (child is ALittleScriptMethodReturnTailDecElement) { m_cache_MethodReturnTailDec = child as ALittleScriptMethodReturnTailDecElement; break; } } return(m_cache_MethodReturnTailDec); }
public override ABnfGuessError CheckError() { ABnfElement parent = null; if (m_element.GetReturnYield() != null) { // 对于ReturnYield就不需要做返回值检查 // 对所在函数进行检查,必须要有async和await表示 // 获取对应的函数对象 ABnfElement element = null; parent = m_element; while (parent != null) { if (parent is ALittleScriptClassMethodDecElement) { var method_dec = parent as ALittleScriptClassMethodDecElement; var modifier = (method_dec.GetParent() as ALittleScriptClassElementDecElement).GetModifierList(); if (ALittleScriptUtility.GetCoroutineType(modifier) == null) { element = method_dec.GetMethodNameDec(); if (element == null) { element = method_dec; } } break; } else if (parent is ALittleScriptClassStaticDecElement) { var method_dec = parent as ALittleScriptClassStaticDecElement; var modifier = (method_dec.GetParent() as ALittleScriptClassElementDecElement).GetModifierList(); if (ALittleScriptUtility.GetCoroutineType(modifier) == null) { element = method_dec.GetMethodNameDec(); if (element == null) { element = method_dec; } } break; } else if (parent is ALittleScriptGlobalMethodDecElement) { var method_dec = parent as ALittleScriptGlobalMethodDecElement; var modifier = (method_dec.GetParent() as ALittleScriptNamespaceElementDecElement).GetModifierList(); if (ALittleScriptUtility.GetCoroutineType(modifier) == null) { element = method_dec.GetMethodNameDec(); if (element == null) { element = method_dec; } } break; } parent = parent.GetParent(); } if (element != null) { return(new ABnfGuessError(element, "函数内部使用了return yield表达式,所以必须使用async或await修饰")); } return(null); } var value_stat_list = m_element.GetValueStatList(); var return_type_list = new List <ALittleScriptAllTypeElement>(); ALittleScriptMethodReturnTailDecElement return_tail_dec = null; // 获取对应的函数对象 parent = m_element; while (parent != null) { if (parent is ALittleScriptClassGetterDecElement) { var getterDec = parent as ALittleScriptClassGetterDecElement; return_type_list.Clear(); var return_type_dec = getterDec.GetAllType(); if (return_type_dec != null) { return_type_list.Add(return_type_dec); } break; } else if (parent is ALittleScriptClassSetterDecElement) { break; } else if (parent is ALittleScriptClassMethodDecElement) { var method_dec = parent as ALittleScriptClassMethodDecElement; var return_dec = method_dec.GetMethodReturnDec(); if (return_dec != null) { var return_one_list = return_dec.GetMethodReturnOneDecList(); foreach (var return_one in return_one_list) { var all_type = return_one.GetAllType(); if (all_type != null) { return_type_list.Add(all_type); } var return_tail = return_one.GetMethodReturnTailDec(); if (return_tail != null) { return_tail_dec = return_tail; } } } break; } else if (parent is ALittleScriptClassStaticDecElement) { var method_dec = parent as ALittleScriptClassStaticDecElement; var return_dec = method_dec.GetMethodReturnDec(); if (return_dec != null) { var return_one_list = return_dec.GetMethodReturnOneDecList(); foreach (var return_one in return_one_list) { var all_type = return_one.GetAllType(); if (all_type != null) { return_type_list.Add(all_type); } var return_tail = return_one.GetMethodReturnTailDec(); if (return_tail != null) { return_tail_dec = return_tail; } } } break; } else if (parent is ALittleScriptGlobalMethodDecElement) { var method_dec = parent as ALittleScriptGlobalMethodDecElement; var return_dec = method_dec.GetMethodReturnDec(); if (return_dec != null) { var return_one_list = return_dec.GetMethodReturnOneDecList(); foreach (var return_one in return_one_list) { var all_type = return_one.GetAllType(); if (all_type != null) { return_type_list.Add(all_type); } var return_tail = return_one.GetMethodReturnTailDec(); if (return_tail != null) { return_tail_dec = return_tail; } } } break; } parent = parent.GetParent(); } // 参数的类型 List <ABnfGuess> guess_list = null; // 如果返回值只有一个函数调用 if (value_stat_list.Count == 1 && (return_type_list.Count > 1 || return_tail_dec != null)) { var value_stat = value_stat_list[0]; var error = value_stat.GuessTypes(out guess_list); if (error != null) { return(error); } bool has_value_tail = guess_list.Count > 0 && guess_list[guess_list.Count - 1] is ALittleScriptGuessReturnTail; if (return_tail_dec == null) { if (has_value_tail) { if (guess_list.Count < return_type_list.Count - 1) { return(new ABnfGuessError(m_element, "return的函数调用的返回值数量超过函数定义的返回值数量")); } } else { if (guess_list.Count != return_type_list.Count) { return(new ABnfGuessError(m_element, "return的函数调用的返回值数量和函数定义的返回值数量不相等")); } } } else { if (has_value_tail) { // 不用检查 } else { if (guess_list.Count < return_type_list.Count) { return(new ABnfGuessError(m_element, "return的函数调用的返回值数量少于函数定义的返回值数量")); } } } } else { if (return_tail_dec == null) { if (value_stat_list.Count != return_type_list.Count) { return(new ABnfGuessError(m_element, "return的返回值数量和函数定义的返回值数量不相等")); } } else { if (value_stat_list.Count < return_type_list.Count) { return(new ABnfGuessError(m_element, "return的返回值数量少于函数定义的返回值数量")); } } guess_list = new List <ABnfGuess>(); foreach (var value_stat in value_stat_list) { var error = ALittleScriptUtility.CalcReturnCount(value_stat, out int return_count, out _); if (error != null) { return(error); } if (return_count != 1) { return(new ABnfGuessError(value_stat, "表达式必须只能是一个返回值")); } error = value_stat.GuessType(out ABnfGuess guess); if (error != null) { return(error); } if (guess is ALittleScriptGuessParamTail) { return(new ABnfGuessError(value_stat, "return表达式不能返回\"...\"")); } error = value_stat.GuessType(out ABnfGuess value_stat_guess); if (error != null) { return(error); } guess_list.Add(value_stat_guess); } } // 每个类型依次检查 for (int i = 0; i < guess_list.Count; ++i) { ALittleScriptValueStatElement target_value_stat = null; if (i < value_stat_list.Count) { target_value_stat = value_stat_list[i]; } else { target_value_stat = value_stat_list[0]; } if (guess_list[i] is ALittleScriptGuessReturnTail) { break; } if (i >= return_type_list.Count) { break; } var error = return_type_list[i].GuessType(out ABnfGuess return_type_guess); if (error != null) { return(error); } if (return_type_guess is ALittleScriptGuessReturnTail) { break; } error = ALittleScriptOp.GuessTypeEqual(return_type_guess, target_value_stat, guess_list[i], false, true); if (error != null) { return(new ABnfGuessError(target_value_stat, "return的第" + (i + 1) + "个返回值数量和函数定义的返回值类型不同:" + error.GetError())); } } return(null); }