나는 가지고있는 사용자 정의 데이터 유형에서 작동하는 F #에서 Linq 표현식 트리를 생성 중입니다. 이 유형은 일반적인 산술 연산자가 오버로드 된 매우 단순한 구분 된 합집합입니다. 하지만 정확한 이유 때문에 정확한 linload 표현식 노드를 만들 수 없다. 문제는, 내가 전에이 작업을 했었다고 맹세하지만, 내가 뭘 바꾸 었는지 알 수 없다.Linq 표현식 트리를 사용하여 연산자 오버로딩을 수행 할 수 없습니다.
문제를 나타내는 작은 코드 샘플을 첨부하겠습니다. 아래 데이터 유형에는 Addition 연산자가 오버로드되어 있습니다. 오버로드 된 연산자를 사용하면 매력처럼 작동하지만 Expression.Add (lhs, rhs)를 사용하여 추가 식 트리 노드를 만들려고하면 시스템이 Add 연산에 대한 오버로드를 찾을 수 없다는 예외를 던집니다.
누구에게 내가 뭘 잘못하고 있는지 아이디어가 있습니까?
module Main =
let createAddOp (lhs:DataType.DataCarrier) (rhs:DataType.DataCarrier) =
let clhs = Expression.Constant(lhs, typeof<DataType.DataCarrier>)
let crhs = Expression.Constant(rhs, typeof<DataType.DataCarrier>)
Expression.Add(clhs, crhs)
또 다른 옵션은 다음과 같습니다
는open System.Linq.Expressions
module DataType =
exception NotImplementedYet of string
type DataCarrier =
| ScalarCarrier of float
| VectorCarrier of float array
member this.Add(other) =
match (this, other) with
| ScalarCarrier(x), ScalarCarrier(y) -> ScalarCarrier(x + y)
| VectorCarrier(u), VectorCarrier(v) ->
VectorCarrier(Array.map2 (fun x y -> x + y) u v)
| _,_ -> raise (NotImplementedYet("No go!"))
static member (+) (lhs:DataCarrier, rhs) =
lhs.Add(rhs)
module Main =
let createAddOp (lhs:DataType.DataCarrier) (rhs:DataType.DataCarrier) =
let clhs = Expression.Constant(lhs)
let crhs = Expression.Constant(rhs)
Expression.Add(clhs, crhs)
(* no problems with this one *)
printf "Testing operator overloading: %A" (DataType.ScalarCarrier(1.0)
+ DataType.ScalarCarrier(2.0))
(* this throws an exception *)
printf "Testing expr construction %A" (Main.createAddOp
(DataType.ScalarCarrier(1.0))
(DataType.ScalarCarrier(2.0)))
환상적이었고, 나는 실제로 해결 방법이 없다고 생각했습니다. 방금 스트레스를 많이 덜어 줬어! +1 나는 이것이 F #의 10 월 CTP 이전에 사용되었다고 생각한다. 내가 시험해 볼게. – Rickard