Trước tiên, bạn nên always assume it's your fault, không phải lỗi của trình biên dịch; select
isn't broken. Bạn có thực sự nghĩ rằng việc thực hiện Visual Studio 2010 của nhà điều hành ??
chưa được thử nghiệm? Khi bạn gặp phải điều gì đó không phù hợp với kỳ vọng của bạn, hãy kiểm tra kỳ vọng của bạn. Nhận hướng dẫn và đảm bảo rằng bạn hiểu chính xác điều gì sẽ xảy ra. Trong trường hợp này, hãy mở đặc tả ngôn ngữ.
Nếu bạn tiến hành §1.4 trong số specification, bạn sẽ thấy một bảng phân nhóm các toán tử thành các nhóm ưu tiên; bạn cũng có thể tìm thấy nó online. Cụ thể, toán tử hợp nhất null ??
nằm gần dưới cùng, phía trên chỉ có toán tử và phép gán ternary có điều kiện thấp và =>
. Đó là bên dưới toán tử cộng. Như vậy, tuyên bố của bạn
string tmp = "a" + "(" + date ?? "blablabla" + ")";
được xử lý bởi trình biên dịch như
string tmp = (("a" + "(" + date) ?? ("blablabla" + ")"));
Tôi sẽ không được hoàn toàn pedantic và cũng nghĩ giải lao biểu thức phụ gia đầu tiên . Kể từ khi rời khỏi tay-side của biểu thức trong tuyên bố đó là không bao giờ null, tất nhiên nó luôn gán "a("
(hoặc "a("
+ date.ToString()
khi date.HasValue
là đúng) để tmp
.
Các chính điểm là bạn có một kỳ vọng không chính xác như những gì nên xảy ra rằng bạn nên đã xác minh chống lại bằng tay.
Nếu tôi đặt date ?? "blablabla"
trong ngoặc đơn, nó được gạch dưới là lỗi.
Tất nhiên rồi. Bạn thậm chí đã đọc thông báo lỗi chưa? Nó có thể cho bạn biết rằng bạn không thể làm ??
trên số DateTime?
và string
vì không có chuyển đổi tiềm ẩn giữa DateTime?
và string
theo một trong hai hướng. Điều này cũng được đề cập trong đặc tả ngôn ngữ; xem §7.13.Bạn phải đọc tin nhắn này và trả lời cho nó. Để có được một cái gì đó ngữ nghĩa tương đương với những gì bạn đang cố gắng để thể hiện, bạn sẽ phải nghỉ mát để các nhà điều hành ternary có điều kiện:
date.HasValue ? date.ToString() : "blablabla"
và sau đó quấn rằng toàn bộ sự việc trong ngoặc vì các nhà điều hành ternary có điều kiện có rất ưu tiên thấp.
Cuối cùng, tôi tìm thấy phiên bản mã hóa chính xác của mã của bạn thay vì xấu xí, không vui để đọc và có thể không thú vị để duy trì. Chỉ cần làm cho nó đơn giản, đề nghị:
var tmp = String.Format("a({0})",
date.HasValue ? date.ToString() : "blablabla");
Bây giờ nó là nên rõ ràng những gì đang xảy ra và những gì sẽ xảy ra. Tôi không phải nghĩ rằng để hiểu điều đó. Lưu suy nghĩ của bạn cho những vấn đề khó khăn bạn sẽ gặp phải.
: Hãy cẩn thận. Chúng tôi sẽ cần phải thêm vào một cuộc gọi phương thức để date.ToString
(trong đó có ưu tiên cao nhất) trước khi cố gắng tìm ra chính xác những gì được đánh giá trước tiên.
Đừng bao quanh 'ngày ?? "blablabla" 'với niềng răng, nhưng với dấu ngoặc đơn, và cho chúng tôi biết nếu điều đó thay đổi một cái gì đó. –
"đây có phải là lỗi trình biên dịch không?" 99,99% thời gian câu trả lời là ** không **. –
Tôi chỉ từng tìm thấy một lỗi trình biên dịch duy nhất, và đó là 20 năm trước. Và đó là một điều dễ dàng để xác nhận trong đó một cuộc gọi được biên dịch thành mã hỏng hóc trong một phiên bản của trình biên dịch cụ thể đó nhưng vẫn hoạt động khác nhau (và chính xác) trong cả hai phiên bản trước và sau. Đây không phải là một trường hợp như thế. – jwenting