2015-08-05 15 views
8

Tôi đang viết các bài kiểm tra đơn vị (MSTest) trong C# 6.0 và tôi nhận thấy một điều gì đó kỳ lạ trong cách trình biên dịch xử lý nội suy chuỗi trong các thuộc tính.Tại sao tôi không thể sử dụng nội suy chuỗi trong một thuộc tính?

Tại sao công việc này:

[TestCategory(nameof(MyClass) + "-UnitTest")] 

Khi điều này không?

[TestCategory($"{nameof(MyClass)}-UnitTest")] 

Bỏ qua thực tế rằng đây có thể không phải là cách tuyệt vời để phân loại thử nghiệm của tôi; Tôi tò mò tại sao trình biên dịch lại cho phép trình biên dịch này chứ không phải trình biên dịch khác.

+0

Tác vụ 'string.Format (" {0} -UnitTest ", nameof (MyClass))' có hoạt động không? – Blorgbeard

Trả lời

6

Khi trình biên dịch gặp một chuỗi nội suy nó ngay lập tức chuyển đổi nó thành một cuộc gọi đến String.Format như vậy ...

[TestCategory($"{nameof(MyClass)}-UnitTest")] 

trở thành ...

[TestCategory(string.Format("{0}-UnitTest", nameof(MyClass)))] 

Attributes require that their arguments be constant expressions nhưng biểu thức trên sẽ không được đánh giá cho đến khi thời gian thực hiện do đó xảy ra lỗi ...

CS0182 Một cuộc tranh cãi thuộc tính phải là một biểu thức hằng số, typeof biểu hiện hoặc mảng biểu hiện sự sáng tạo của một kiểu tham số thuộc tính ...

Bạn biết tất cả các thông tin sẵn tại thời điểm biên dịch nhưng trình biên dịch là không đủ thông minh để tìm ra.

nameof hoạt động hơi khác so với chuỗi nội suy vì nó là evaluated at compile-time do đó không có lỗi.

6

Chuỗi nội suy không phải là giá trị không đổi. Giá trị được xác định trong thời gian chạy, mặc dù trong trường hợp của bạn, tất cả các đầu vào có thể được tính toán tại thời gian biên dịch.

0

Nội suy chuỗi xảy ra trong runtime và các thuộc tính có mặt trong compile time. Vì vậy, trình biên dịch của bạn không thể giải quyết này, vì nó sẽ được biên dịch như sau:

luận
[TestCategory(new FormattableString 
    { 
    Format = "{0}-UnitTest", 
    Args = new object[] { nameof(MyClass)} 
    })] 
3

Một thuộc tính có phải là một hằng số thời gian biên dịch. Trong khi nameof() là một hằng số (xem Is nameof() evaluated at compile-time?), thì tính năng nội suy chuỗi không phải là.

Biểu thức chuỗi nội suy tạo chuỗi bằng cách thay thế các biểu thức có chứa ký tự đại diện cho kết quả của biểu thức.

Các vấn đề liên quan