2009-01-14 30 views
20

Thông thường, khi tôi sử dụng lambdas, tôi chỉ sử dụng "a, b, c, d ..." làm tên biến vì các loại được suy ra một cách dễ dàng và tôi tìm thấy tên ngắn để dễ đọc hơn. Dưới đây là một ví dụ:Tên biến Lambda - viết tắt tên hoặc không viết tắt tên?

var someEnumerable = GetSomeEnumerable(); 
var somethingElseList = someEnumerable.Select(a => a.SomeProperty) 
             .OrderBy(a => a.SomePropertyField); 
var someDictionary = somethingElseList.ToDictionary(a => new SomeClass(a.Prop1), 
                a => a); 

Một số câu hỏi đặt tên này, và muốn để xem dài gõ ra tên, như thế này:

var someEnumerable = GetSomeEnumerable(); 
var somethingElseList = someEnumerable.Select(importantObj => importantObj.SomeProperty) 
             .OrderBy(objsInfo => objsInfo.SomePropertyField); 
var someDictionary = somethingElseList.ToDictionary(theInfoId => new SomeClass(theInfoId.Prop1), 
                theInfoId2 => theInfoId2); 

Kể từ phạm vi rất hẹp (giữa dấu ngoặc), trừ trường hợp bạn đang nhận được ngu ngốc và làm tổ họ, tôi tìm thấy nó dễ dàng hơn để đọc tên ngắn.

Không bị cuốn vào các ví dụ đặt tên ngớ ngẩn tôi đã sử dụng ở trên, sự đồng thuận chung về tên biến Lambda là gì? Tên viết tắt, hoặc không viết tắt tên?

Trả lời

30

Cách tôi thường làm tùy thuộc vào bộ sưu tập bạn đang liệt kê. Nếu tên của bộ sưu tập ngụ ý loại tham số lambda sẽ là gì, thì tôi chỉ cần đi với một chữ cái duy nhất, tuy nhiên nếu bộ sưu tập không phải là mô tả, thì tôi sẽ sử dụng một từ.

IE:

myCollection.Where(person =>....); //non descriptive collection name 

myPeopleCollection.Where(p=>...); // descriptive collection name 
9

Tôi cố gắng sử dụng tên một từ nhưng có ý nghĩa. Vì vậy, tôi sẽ có xu hướng để sử dụng "người" thay vì "p" nhưng sẽ không đi cho "newlyAddedPerson".

này đi cho các biểu thức truy vấn cũng - Tôi cũng có thể vi phạm này trong các ví dụ throwaway nhanh chóng, nhưng tôi không nói chung thích:

from p in source 
where p.Age > 10 
select p.Name; 

tôi đã xa chứ không phải nhìn thấy

from person in source 
where person.Age > 10 
select person.Name; 
+0

có, tôi có xu hướng đặt tên tốt hơn trong cú pháp biểu thức, nhưng đó là vì phạm vi rộng hơn và có thể trở nên khó hiểu. – TheSoftwareJedi

+1

Trong cú pháp biểu thức, tôi thường đặt tên các tên dài hơn vì phạm vi rộng hơn. Tôi không thấy điểm viết .OrderBy (theInt => theInt) thay vì .OrderBy (a => a). – TheSoftwareJedi

+1

Nó làm cho nó rõ ràng hơn những gì các yếu tố là tại điểm đó của truy vấn. Nó không phải luôn luôn rõ ràng, thật không may. –

5

Tôi thích điều shortname. Tôi làm việc đó mọi lúc. Tôi chủ yếu sử dụng i, y, x trong lambdas, nhưng tôi sử dụng a, b, c, d trong sql.

2

Nó có thể được yêu cầu rất nhiều để đặt một câu hỏi cho 'đồng thuận' bật 'đặt tên'. :)

Tôi đồng ý rằng 'tầm quan trọng của tên tốt' tỷ lệ thuận với phạm vi của tên. Câu trả lời của thích

from person in source ... 

Jon Skeet là hấp dẫn, nhưng nếu tên được sử dụng rất nhiều và đặc biệt là nếu đầu vào được đặt tên tốt hơn, tôi nghĩ rằng tôi thích

from p in persons ... 
+1

Tôi thấy đặt câu hỏi đặt tên trong cú pháp biểu thức khác với đặt tên trong cú pháp lambda. – TheSoftwareJedi

3

Tôi muốn nói rằng tôi đồng ý với BFree. Điều đó, đối với tôi, nó sẽ phụ thuộc vào bối cảnh, nhưng tôi luôn cố gắng làm cho nó trở thành 'súc tích' càng tốt. Chú ý tôi nói ngắn gọn, và không ngắn gọn hay ngắn gọn.

Dưới đây là hai ví dụ trong phương ngữ LISP Clojure:

user=> (def names ["ryan" "bob" "tom" "tim"]) 
#'user/names 

user=> (filter (fn [name] (.startsWith name "t")) names) 
("tom" "tim") 

Đối với những người không biết Lisp/Clojure, lambda của tôi là lập luận với chức năng 'lọc'. Tức là, "(fn [name] ....)". Tôi đã chọn sử dụng 'tên' ở đây vì nó ngắn nhưng mô tả chính xác những gì tôi đang làm việc. Tuy nhiên, tôi nghĩ rằng một 'a', 'i', 'x', v.v ... sẽ chỉ có thể đọc được.

user=> (def odds (iterate (fn [n] (+ n 2)) 1)) 
#'user/odds 

user=> (take 5 odds) 
(1 3 5 7 9) 

Ở đây, tôi chỉ sử dụng 'n' để đứng cho 'số'. Tôi nghĩ rằng 'số' sẽ là OK quá, nhưng hơi quá chi tiết cho khẩu vị của tôi.

Tôi chắc chắn KHÔNG sử dụng tên 'nameOfPerson' hoặc 'previousOddNumber'. Đó chỉ là WAY quá nhiều thông tin. Tôi cũng cố gắng giữ cho các loại ngoài tên của tôi hầu hết thời gian, ví dụ: 'nameString'. Tôi tìm thấy những thứ như vậy, hầu hết thời gian, là thông tin thừa.

Cá nhân, tôi nghĩ rằng các tên chi tiết hơn như vậy có xu hướng xuất phát từ ý tưởng rằng nó giúp tài liệu mã. Nó đặc biệt phổ biến trong các ngôn ngữ như Java/C# nó có vẻ. Tôi nghĩ rằng điều này có thể được lập luận theo cả hai cách, tùy thuộc vào phong cách của lập trình viên. Tuy nhiên, tên càng dài thì mã càng chặt (đọc giòn) có thể trở thành. Nếu tên của tôi là rất cụ thể, và đó là một chức năng thay đổi thường xuyên, sau đó rất có thể là tên sẽ phải thay đổi rất nhiều. Cuối cùng, DEV có thể trở nên lười biếng và bạn sẽ kết thúc với một cái tên không thực sự mô tả biến được sử dụng cho cái gì. Đây không phải là một vấn đề, nếu và chỉ khi lập trình viên không giả định tên là chính xác. Cấp, điều này có thể được tìm ra nhanh chóng trong quá trình biên dịch (vì lập trình viên sẽ cố gắng phân chia hai chuỗi hoặc một số thứ như vậy), nhưng nó có thể gây lãng phí thời gian và sự nhầm lẫn trong các dự án lớn hơn.

Tôi cũng sẽ tranh luận về sự phù hợp vì màn hình bất động sản. Tôi vẫn cố gắng bọc các hàng của mình ở 80 cột rộng, và thật khó khi 'myVaraibleNameIsAsLongAsAParagraph'.

Cuối cùng, tôi nghĩ rằng nó luôn luôn đi xuống để thỏa hiệp. Vì vậy, họ không thích 'a', nhưng có lẽ họ có thể đồng ý rằng bạn nên cố gắng cho một từ tên như 'người' hoặc 'số', và tránh trường hợp lạc đà khủng khiếp đó.

Xin lỗi vì cuốn sách.

+0

+1 Cảm ơn sách – TheSoftwareJedi

1

Tôi đi với một, hai hoặc ba chữ cái, tạo thành một biểu diễn viết tắt của đối tượng được đề cập.

Persons.Where(p => ...) 
AnalysisCode.Where(ac => ...) 
1

Theo nguyên tắc chung, tôi nghĩ bạn càng rõ ràng với tên biến/đối tượng/phương thức càng tốt. Vì chúng ta thường dành phần lớn thời gian của chúng tôi để đọc mã của người khác, chúng tôi càng dễ dàng hiểu nhanh hơn bạn có thể tập trung vào cú pháp và vào logic. Những ngày này với IntelliSense và tương tự, nó không thực sự là một gánh nặng để sai lầm ở mặt bên của sự rõ ràng bất cứ khi nào có thể.

0

Tôi đồng ý với @Johnny Wey; đặt tên cho các biến của bạn - cho cùng một lý do bạn đặt tên cho chúng trong bất kỳ mã nào khác! Không hiểu sự định trước này tránh xa sự rõ ràng chỉ vì bản chất "trực tuyến" của mã. Dễ đọc là chìa khóa - trong nháy mắt/w/out phải "di chuột" trên các công cụ; nếu không, bạn cũng có thể nói không biến nào cần được đặt tên phù hợp. Có lẽ một chút sai lầm nếu được sử dụng với một cái gì đó "Enuerable", nhưng vẫn còn tốt đẹp để xem (một lần nữa trong nháy mắt) những gì các mã heck đang làm. Nếu suy luận kiểu biến là dựa vào một số loại chung được chuyển vào lớp hoặc một cái gì đó, hãy gọi tên nó. Làm cho tất cả các mã đọc như một câu; các máy tính được cho là thích nghi với chúng ta ("nhân bản"), không phải là cách khác để chúng ta bắt đầu hành động như máy tính và trở nên khó hiểu chỉ vì chúng ta có thể/cảm thấy thông minh hơn/giống như những người đam mê công nghệ cao hơn. kno!). Thật dễ dàng để gõ một tên rõ ràng và bạn vẫn có tất cả các tùy chọn hoàn thành Intellisense/câu bạn làm trong các phương thức được đặt tên. Ngoài ra, lơ lửng trong trường hợp lambdas không phải lúc nào cũng cung cấp cho bạn thông tin về var (bực bội trong khi gỡ lỗi), vì vậy thật tuyệt khi thấy tên "rõ ràng/đại diện đủ", đặc biệt là cho những người mới phát triển. có thể suy ra các loại bằng cách duyệt qua ngữ cảnh câu lệnh (cũng có thể khó hiểu).

0

Rút ngắn sẽ tốt hơn nếu mục đích của biến rõ ràng.Lambdas gọi cho một phong cách chức năng của văn bản, do đó bạn thấy rất nhiều chuỗi trong một dòng duy nhất. Sạch hơn của nó để xem khi bạn giữ chúng ngắn.

Một trường hợp khác là đôi khi bạn cần khai báo biến giả không có sự liên quan/ý nghĩa trong phạm vi đó. Trong những trường hợp như vậy, tôi sử dụng _ làm cho nó rõ ràng cho tôi. Điều này xuất phát tiện dụng đặc biệt trong phương pháp quá tải, cho ví dụ,

public Foo Do() 
{ 
    return Do(_ => true); 
} 

public Foo Do(Func<T, bool> pattern) 
{ 
    return SomethingElse(pattern); 
} 
0

Dựa trên các câu trả lời ở trên, tôi nghĩ rằng có sự đồng thuận chung rằng, nếu bạn không thể nói từ bối cảnh những gì bạn đang đối phó với, sử dụng một mô tả tên là tốt hơn. Ví dụ:

entities.Where(person => person.Age >= 21); 

Trong trường hợp bối cảnh rõ ràng, tuy nhiên, một cái tên duy nhất chữ có thể thực sự giúp dễ đọc, bởi vì nó làm cho nó dễ dàng hơn để tập trung vào các thông tin quan trọng. Ví dụ:

people.Where(p => p.Age >= 21); hoặc people.Where(x => x.Age >= 21);

Câu hỏi đặt ra là, mà là tốt hơn, p hoặc x?

  • Trong ủng hộ p, đó là một mô hình quen thuộc trong các truy vấn SQL và cung cấp thêm một chút nhắc nhở rằng bạn đang nói về một Person.
  • Ưu tiên x, nếu bạn đổi tên Person thành Customer, bạn không phải lo lắng về việc sửa tất cả thông số lambda của mình. Nếu bạn đã sử dụng p, nó sẽ thực sự là một chút khó hiểu nếu mã của bạn đã trở thành customers.Where(p => p.Age >= 21), trong khi x về cơ bản là không thuyết phục.

Gần đây tôi đã bắt đầu sử dụng x và cho đến nay, tôi đã không nhận thấy bất kỳ nhược điểm đáng kể nào, nhưng vui lòng nhận xét nếu bạn không đồng ý.

3

Nhóm của chúng tôi không cho phép các biến thư đơn, không phải sự kiện trong lamdas.

Những gì chúng tôi thấy là, giống như trong TSQL, mã càng dài thì càng khó hiểu. Theo như lambda của

Chúng tôi sẽ làm một cái gì đó như thế này:

people.Where(personFound => personFound.FirstName.Contains("blah!")); 

Bằng cách đó dev tiếp theo sẽ không phải nhìn vào

people.Where(p => p.FirstName.Contains("blah")); 

Dường như có thể đọc được, nhưng nó luôn luôn làm lúc đầu

Điều gì về tham gia

citizenShip.Join(people, c => c.personid, p => p.persoinid, (p, c) => new { p.FirstName, c.IsCitizen}) 
.Where(pc => pc.FirstName.Contains("blah"); 
.210

cùng với tên biến

citizenShip.Join(people, 
       citizenToJoin => citizenToJoin.personid, 
       personToJoin => personToJoin.persoinid, 
       (joinedPerson, joinedCitiznship) => 
        new { joinedPerson.FirstName, joinedCitiznship.IsCitizen}) 
.Where(personAndCitizenshipFound=> personAndCitizenshipFound.FirstName.Contains("blah"); 

Oh nhưng điều này là khó hiểu và xấu xí. Chỉ cần sử dụng các chữ cái differenct để nó ít khó hiểu hơn

citizenShip.Join(people, 
       c => c.personid, 
       p => p.persoinid, 
       (jp, pc) => 
        new { jp.FirstName, jc.IsCitizen}) 
.Where(pc => pc.FirstName.Contains("blah"); 

Vẫn còn khó hiểu, nhưng bây giờ còn tồi tệ hơn.Vì vậy, chúng tôi phá vỡ lambda lên để chúng tôi refactor cho dễ đọc

var peopleWithCitizenship = citizenShip.Join(people, 
              citizenToJoin => citizenToJoin.personid, 
              personToJoin => personToJoin.persoinid, 
              (joinedPerson, joinedCitiznship) => new { joinedPerson.FirstName, joinedCitiznship.IsCitizen}); 

var peopleWithCitizenshipFilteredByName = peopleWithCitizenship.Where(personAndCitizenshipFound=> personAndCitizenshipFound.FirstName.Contains("blah")); 

Đây không phải là một ví dụ hoàn hảo nhưng làm cho mã có thể đọc được với kiến ​​thức nội bộ rất ít. Chúng tôi thấy điều này cho thấy mã phức tạp (lambda) cần được chia thành các phần nhỏ hơn.

+0

Ồ. tất cả các đối số cho một chữ cái đều giống nhau khi chúng ta chuyển đi khỏi các biến thư đơn trong mã khác. Tất cả bạn phải làm là nhìn vào một số TSQL với một loạt các bí danh chữ cái duy nhất hoặc lamda nơi devs nhấn mạnh vào văn bản như SQL, với một loạt các tham gia và lựa chọn. –

+0

+1. Chúng tôi đã có một số gà thích làm nhiều gia nhập rất lớn với sáu hoặc mười bảng khác nhau, bí danh a, b, c, vv Thật là kinh khủng. –

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