介绍:
根据我的理解,类型声明{typeλ[α] = Either [A,α]}代表任何类型的其他类型的λ[α]作为其成员(与方法是类的成员完全相同的意义).这是一种结构类型,即其结构是具有类别别名声明λ[α]作为其成员.
另一方面,({typeλ[α] = [A,α]})#λ仅由于通过#的投影类型而仅为λ.
题:
为什么在进行类型投影时,{typeλ[α] = [A,α]}周围需要括号?为什么不只是{typeλ[α] = [A,α]}?λ?
换句话说,根据Scala Type declaration grammar(见下文),({typeλ[α] = Either [A,α]})#λ的精确解析树是什么?
为什么{typeλ[α] = [A,α]}#λ在这个语法中不是一个正确的“句子”?
Type ::= FunctionArgTypes ‘=>’ Type | InfixType [ExistentialClause] FunctionArgTypes ::= InfixType | ‘(’ [ ParamType {‘,’ ParamType } ] ‘)’ ExistentialClause ::= ‘forSome’ ‘{’ ExistentialDcl {semi ExistentialDcl} ‘}’ ExistentialDcl ::= ‘type’ TypeDcl | ‘val’ ValDcl InfixType ::= CompoundType {id [nl] CompoundType} CompoundType ::= Annottype {‘with’ Annottype} [Refinement] | Refinement Annottype ::= SimpleType {Annotation} SimpleType ::= SimpleType TypeArgs | SimpleType ‘#’ id | StableId | Path ‘.’ ‘type’ | ‘(’ Types ‘)’ TypeArgs ::= ‘[’ Types ‘]’ Types ::= Type {‘,’ Type}
解决方法
你也需要考虑
CompoundType ::= Annottype {‘with’ Annottype} [Refinement] | Refinement Refinement ::= [nl] ‘{’ Refinestat {semi Refinestat} ‘}’ Refinestat ::= Dcl | ‘type’ TypeDef |
非正式描述
#只能遵循SimpleType,但是{typeλ[α] = [A,α]}是一个Refinement,最终是一个Type.
从通用类型获取SimpleType的唯一方法是用括号括起来.
正式推导
SimpleType '(' Types ')' '#' id '(' Type ')' # id '(' InfixType ')' # id '(' CompoundType ')' # id '(' Refinement ')' # id '(' '{' Refinestat '}' ')' # id '(' '{' 'type' TypeDef '}' ')' # id ... ({ type λ[α] = Either[A,α] })#λ