cuốn sách gpt4 ai đã làm

c# - Chuyển đổi biểu thức getter chung thành biểu thức getter đối tượng

In lại Tác giả: Vũ trụ không gian Thời gian cập nhật: 2023-11-03 23:32:46 29 4
mua khóa gpt4 Nike

Tôi có một trình thiết lập/getter biểu thức như thế này:

biểu thức var = () => SomeInstance.Nr;

Nó được truyền vào một phương thức:

public void AddExpression(Biểu thức<>> func)

Bây giờ tôi muốn chuyển đổi biểu thức chung này thành

Biểu thức<>>

Tôi không chắc mình có thể làm được điều này. Tôi đã thử một cái gì đó như thế này:

var đã chuyển đổi = Expression.Convert(func, typeof(object));
var objectExpression = Expression.Lambda<>>(Expression.Call(converted.Method), func.Parameters);

Nhưng khi tôi gọi

số var = objectExpression.Compile()();

Nó không trả về giá trị thuộc tính.

Mã có thể được kiểm tra ở đây: http://volatileread.com/utilitylibrary/snippetcompiler?id=25062

gia hạn:Có vẻ như cuộc gọi được kết thúc lần thứ hai:

var đã chuyển đổi = Expression.Convert(func, typeof(object));
var objectExpression = Expression.Lambda<>>(Expression.Call(converted.Method), func.Parameters);
var anotherDelegate = objectExpression.Compile().Invoke(); // lẽ ra phải có giá trị ở đây
var value = ((Delegate)anotherDelegate).DynamicInvoke(); // cái này bây giờ trả về giá trị

câu trả lời hay nhất

không sử dụng Biểu thức.CallTrên đại biểu - đó chỉ dành cho các phương thức gọi điện. Thay vào đó, bạn muốn sử dụng Biểu thức.Invoke , được sử dụng đặc biệt để gọi các đại biểu. Hơn nữa, chìa khóa để thực hiện cây biểu thức là包装 - Gọi đại biểu bên trong, chuyển đổi kết quả và gói nó trong lambda:

Biểu thức<>> inputExpression = () => 42;

var newLambda =
Biểu thức.Lambda<>>
(
Biểu thức.Convert
(
Expression.Invoke(inputExpression),
loại(đối tượng)
)
);

Console.WriteLine(newLambda.Compile()()); // In 42.

mớiLambdaĐúngBiểu thức<>>và gọi nó cho bạn 42 , như bạn có thể mong đợi.

Tất nhiên, điều này làm cho việc thực hiện điều này như một phương pháp mở rộng trở nên khá dễ dàng (mặc dù bạn có thể muốn sử dụng các mẫu để tạo tất cả các phương thức khác nhau). Chức năng<...> quá tải).

Lưu ý rằng điều này chỉ đúng nếu bạn đang sử dụng bất kỳ nhà cung cấp LINQ nào支持Điều này sẽ chỉ hoạt động khi Gọi - Trong trường hợp này, đó không phải là vấn đề vì trình biên dịch lambda có thể xử lý nó, nhưng nếu bạn cần sử dụng thứ gì đó như thế này, ví dụ như EntityFramework, bạn cần thực hiện một cách tiếp cận hơi khác - bạn cầnMở rộngLambda bên trong, biến đổi phần thân của lambda bên trong và bọc nó lại trong một lambda khác. Đối với các biểu thức không tham số, điều này thật dễ dàng:

Biểu thức<>> inputExpression = () => 42;

var newLambda =
Biểu thức.Lambda<>>
(
Expression.Convert(inputExpression.Body, typeof(object))
);

Console.WriteLine(newLambda.Compile()()); // In 42.

Ngoài ra, để hoàn thiện hơn, hãy lưu ý rằng điều này chỉ hoạt động nếu biểu thức bên trong thực sự là một biểu thức không đổi và không được trích dẫn - nhưng nếu bạn cần các biểu thức lồng nhau được trích dẫn, có thể bạn sẽ không hỏi câu hỏi này: D

Về C# - chuyển đổi biểu thức getter chung thành biểu thức getter đối tượng, chúng tôi đã tìm thấy một câu hỏi tương tự trên Stack Overflow: https://stackoverflow.com/questions/31557138/

29 4 0
không gian vũ trụ
Hồ sơ

Tôi là một lập trình viên xuất sắc, rất giỏi!

Nhận phiếu giảm giá taxi Didi miễn phí
Phiếu giảm giá taxi Didi
Chứng chỉ ICP Bắc Kinh số 000000
Hợp tác quảng cáo: 1813099741@qq.com 6ren.com
Xem sitemap của VNExpress