2009-02-12 31 views
5

Khi bạn gặp phải đang hoạt động mã không phù hợp với mắt, bạn có khả năng tái cấu trúc mã đó như thế nào? Tôi biết mã thẩm mỹ chủ yếu là chủ quan, nhưng tôi bị làm phiền rất nhiều bởi mã "xấu xí" và thấy khó cưỡng lại sự thôi thúc làm sạch nó.Bạn có buộc phải loại bỏ cú pháp cú pháp không?

tôi không thích:

chức năng nặng làm tổ

AndFinally(AndThenDoThis(DoThis(strVar, 1, DoThat("February"))), FetchValue(0)) 

Bất kỳ ngoặc hơn, dấu phẩy, và ampersands hơn mức cần thiết

CType(ctlGrid.DataSource, DataView).RowFilter = "HourlyRate > 100.00" 

và sẽ cân nhắc việc thêm một phương pháp (hoặc phương pháp khuyến nông) để có được

ctlGrid.DataView.RowFilter = "HourlyRate > 100.00" 

luân phiên, tôi sẽ thay đổi:

rows = tblEmp.Select("AnnualEarnings > " & dEarnings.ToString & " AND Position = '" & strPosition & "'") 

này:

rows = tblEmp.Select("AnnualEarnings > ? AND Position = ?", dEarnings, strPosition) 

Bây giờ đây là một chút cực đoan, nhưng tôi thậm chí sẽ mất một thành ngữ phổ biến, giống như việc tìm kiếm mục đầu tiên trong một mảng và cung cấp phương thức cho nó:

row = tblEmps.Select("Position = 'Manager'")(0) 

be đến (và, tôi nghĩ, là dễ đọc hơn):

row = tblEmps.Select("Position = 'Manager'").First 

Khi tôi thấy điều này nó làm tôi điên

frmMain.grdEmployees.colName.Bold = True 
frmMain.grdEmployees.colName.Font = "Arial" 
frmMain.grdEmployees.colName.BackColor = "lightyellow" 

và, đối với những gì tôi tìm thấy dễ dàng hơn với đọc, tôi kết thúc lên với:

With frmMain.grdEmployees.colName 
    .Bold = True 
    .Font = "Arial" 
    .BackColor = "lightyellow" 
End With 

Tôi có thể tiếp tục với điều này. Tôi tập thể dục chăm sóc tuyệt vời để tái cấu trúc chỉ thỉnh thoảng dẫn đến việc giới thiệu một lỗi - thường là một lỗi ngắn, có tác động thấp.

Không phải tất cả mọi người trong công ty của chúng tôi đều đồng ý với loại điều này, nhưng tôi tin rằng đó là một lợi ích để bảo trì lâu dài. Tôi đọc "Don't Make Me Think "của Steve Krug vài năm trước. Tôi cho rằng cuốn sách này (mặc dù hướng tới thiết kế web) ủng hộ mã được viết theo cách mà nó giảm thiểu nỗ lực tinh thần cần thiết để tiêu hóa nó. Trong hầu hết các trường hợp, với tôi, điều này có nghĩa là thể hiện cùng một mã trong ít dòng hơn, nhưng không bao giờ theo một cách phức tạp, khó hiểu. trong? bạn có xem xét thực tế điều này có lợi hơn hay có hại nhiều hơn?

+0

Đó dường như là những đặc điểm tốt. Mặc dù nó giúp nếu ngôn ngữ cho vay chính nó để làm việc xung quanh vấn đề như vậy (chẳng hạn như parens thêm). – MichaelGG

+0

Một số trong số này là hiển nhiên, nhưng một số là chủ quan. Cá nhân tôi không thích khối "với". –

Trả lời

7

Với tôi, điều quan trọng nhất không phải là tính thẩm mỹ mà cho dù ai đó có thể hiểu được mã sau này.

Cuộc gọi hàm lồng nhau thường là không có, bởi vì gánh nặng nhận thức của việc hiểu toàn bộ biểu thức trở nên cao. Và có thể có tác dụng phụ trong các cuộc gọi lồng nhau, điều này làm cho mọi việc tồi tệ hơn nhiều. Vì vậy, tốt là phá vỡ tổ và giới thiệu các biến tạm thời, cũng bởi vì sau đó bạn có thể viết các chú thích trong mã và giải thích kết quả trung gian là gì.

Giới thiệu ký pháp mới cho tầm thường (ví dụ: (0) so với ví dụ đầu tiên) không tốt, vì nó không cải thiện sự hiểu biết: bạn đang tạo một khái niệm trừu tượng mới mà không thêm giá trị. Tại sao viết i.addOne() nếu bạn có thể làm điều đó với i + +? Mọi người đều biết những gì "++" là về, nhưng họ không thể biết những gì addOne() thực sự không đọc tài liệu của nó. Vì vậy, nó chỉ là một cách để thêm gánh nặng nhận thức.

Bạn tham khảo cấu trúc lại, nhưng việc tái cấu trúc không có nghĩa là chỉ thay đổi bố cục mã và tính thẩm mỹ, mà còn thay đổi cấu trúc cho toàn bộ chương trình. Tiếp tục với ví dụ của bạn, các hàm gọi hàm f (x (y (z (q))) có thể báo hiệu cần phải tái cấu trúc vượt quá tính thẩm mỹ: tìm ra lý do tại sao các cuộc gọi lồng nhau là cần thiết và sau đó đóng gói chúng thành một sự trừu tượng mới . Tất nhiên việc tái cấu trúc cũng có thể thay đổi mô hình đối tượng hoàn chỉnh, một nỗ lực lớn.

+0

Tôi đã xem xét điểm thứ hai của bạn liên quan đến (0) so với trước. Trước và Tôi tôn trọng nó. Nó dường như đến từ triết lý Python (một cách ưa thích) so với triết lý của Ruby về tính linh hoạt tối thượng. Tôi bắt đầu nghiêng về phía Python. Điểm tốt! – Mario

0

trong hầu hết các tổ chức, có một phương châm thiết lập cho phong cách.

+0

http://xkcd.com/285/;) – ng5000

0

làm cho cảm giác.

Tôi sẽ sử dụng ví dụ này làm ví dụ. firstManagerow = tblEmps.Select("Position = 'Manager'").First

Tốt hơn nên xác định các biến tại các địa điểm, nơi tốt nhất nên sử dụng chúng trong gỡ lỗi.

Điều này có thể trở thành phương pháp có tên mô tả phù hợp.

rows = tblEmp.Select("AnnualEarnings > " & dEarnings.ToString & " AND Position = '" & strPosition & "'")

0

tôi cố gắng để thoát khỏi những điều xấu xí là tốt, resharper giúp tôi rất nhiều khi phát triển các ứng dụng .NET để cho tôi gợi ý về initializers đối tượng ví dụ.

Bạn cũng có thể định cấu hình IDE để thiết lập các quy tắc định dạng mã nguồn thích hợp mà bạn và nhóm của bạn nên sử dụng. Điều này không loại trừ các tình huống mà bạn muốn xem các trình định dạng chuỗi hoặc có thể một số dòng phụ nhưng tôi nghĩ nó sẽ giúp ích rất nhiều. Đối với phần còn lại có resharper :).

14

Khi tôi bắt đầu lập trình, mọi dòng mã tôi thấy bắt buộc phải chỉnh sửa. Nhìn lại, tôi lãng phí rất nhiều thời gian cho việc đó. Những ngày này, tôi vẫn sửa chữa những gì tôi cho là mã xấu xí, nhưng chỉ khi nó ở trong một tập tin mà tôi đang thay đổi vì những lý do thực tế.

Tránh sự cám dỗ để chỉnh sửa toàn bộ cơ sở mã vì lý do phong cách.

+0

+1 về cảnh báo chống lại việc chỉnh sửa không có lý do chính đáng ... –

+0

0 vì bạn chắc chắn đã học được rất nhiều bằng cách chỉnh sửa quá :) – Leonidas

+0

@Leonidas: Có thể. Nhưng tôi chắc chắn rằng tôi lái xe các đồng nghiệp của tôi hạt! –

4

Tôi là tất cả để thẩm mỹ mã, nhưng mong muốn thay đổi mã hiện tại, đặc biệt nếu mã hoạt động, nên được chống lại càng nhiều càng tốt. Hướng dẫn về kiểu mã nên được thiết lập và thực thi, nhưng mã hiện tại phải được xử lý cẩn thận: rất dễ thực sự thay đổi cách mã hoạt động.

0

Mặc dù tôi đã đọc khá nhiều sách về cách sử dụng tên biến mô tả, khi tôi viết một hàm ngắn chỉ hoạt động với một vài biến, tôi thường chọn tên ngắn (thậm chí chung chung). Dài, tên mô tả có thể tiêu thụ rất nhiều bất động sản trực quan và cho các chức năng cơ bản, tôi xem xét nó quá mức cần thiết. Nếu các hàm cơ bản phát triển để bao gồm độ phức tạp bổ sung và nhiều biến được giới thiệu, tôi sẽ mở rộng các tên để cải thiện độ rõ ràng.

For i As Integer = 0 To tblEmps.Rows.Count - 1 
    Console.WriteLine(tblEmps.Rows(i)("Name")) 
Next 

tôi thấy không có lý do tại sao i nên mô tả nhiều hơn.

+0

Về vấn đề đó, hãy xem http://stackoverflow.com/questions/101070/what-is-an-ideal-variable-naming- quy ước-cho-loop-biến và http://stackoverflow.com/questions/130775/is-a-variable-named-i-unacceptable/130787 –

3

Có rất nhiều câu trả lời mâu thuẫn thể này bắt nguồn từ những cân nhắc khác nhau, nhưng có rất nhiều ví dụ của bạn là những vấn đề của phong cách mà dư luận có thể khác nhau ...

  • Có một tiêu chuẩn thành lập? Nếu vậy, liệu có một nền văn hóa đã được thiết lập để tái cấu trúc mã hiện có cho nó, và cũng đảm bảo rằng nhà phát triển đã viết nó nhận thức được? Nếu không, bạn có nguy cơ vi phạm ý thức phong cách của người khác và tham gia vào cuộc chiến chỉnh sửa. Nếu không có biện pháp phòng ngừa (dưới hình thức tiêu chuẩn và đánh giá), thì có những câu hỏi lớn hơn liệu bạn có nên "sửa" nó hay không.
  • Có sự lặp lại phù hợp với việc tái cấu trúc không? Giới thiệu một phương pháp để xử lý một trường hợp đơn giản không phải lúc nào cũng thích hợp
  • Bạn có thực sự đang làm việc với mã bit đó hoặc chỉ sử dụng mã đó không? Nếu bạn không cần phải làm cho bàn tay của bạn bẩn và mã hoạt động, hãy xem xét để lại nó một mình.
  • Bạn có khả năng viết nhiều mã hơn và giới thiệu phức tạp hơn vì lợi ích của thẩm mỹ không? Việc giới thiệu quá nhiều phương pháp mới có thể gây nhầm lẫn như nhiều dấu ngoặc lồng nhau.

Nhóm tôi làm việc với các cuộc thảo luận thường xuyên về các vấn đề phong cách và đôi khi chúng tôi đồng ý về tiêu chuẩn, nhưng thường trong những vấn đề ít quan trọng hơn, chúng tôi nhận thấy tốt hơn là đồng ý và không lịch sự để tránh chỉnh sửa quyết liệt, nơi chỉ có sự khác biệt về ý kiến.

Cuối cùng, chi phí thời gian và rủi ro của tất cả các chỉnh sửa này tăng lên và cần phải được cân nhắc so với thời gian chi tiêu hiệu quả hơn.

0

Chỉ refactor nếu bạn cần giả định đây là một liên doanh thương mại. Ví dụ Nesting Heavy Function của bạn sẽ là nơi mà việc gỡ lỗi đột nhập vào nhiều dòng làm cho cuộc sống trở nên dễ dàng hơn nhiều. Loại bỏ dấu ngoặc đơn dễ mắc lỗi hơn nhiều. Yeah nó có thể nhìn tốt hơn nhưng tốt thực sự không phải là bất kỳ dễ đọc hơn/tốt hơn. Nó chỉ là nhiều hơn trong phong cách bạn đang sử dụng để nhìn thấy.

2

tôi cảm nhận được hai câu hỏi riêng biệt ở đây:

  1. nên mã được refactored để cải thiện rõ ràng?
  2. Mã có nên được cấu trúc lại không vì lý do nào khác để cải thiện độ rõ ràng không?

Theo tôi, câu trả lời cho câu hỏi đầu tiên thường là "có". Tất cả mã nên, lý tưởng là tự tài liệu nhiều hơn hoặc ít hơn. Ít thời gian hơn để cố gắng để hiểu mã có nghĩa là có nhiều thời gian hơn để chi tiêu sửa lỗi khi gặp sự cố. Khi bạn đi sâu vào mã để sửa chữa một cái gì đó, nó hoàn toàn có thể được giá trị nỗ lực để làm rõ bất cứ điều gì mà làm cho bạn gãi đầu của bạn.

Nhưng điều đó dẫn chúng ta đến câu hỏi thứ hai nguy hiểm. "Khi bạn đi sâu vào mã để khắc phục điều gì đó" là bởi đến nay phần quan trọng hơn của tuyên bố đó. Nếu bạn không có lý do để thay đổi một cái gì đó khác hơn là để làm cho nó dễ dàng hơn để đọc, sau đó vì lợi ích, đóng trình soạn thảo của bạn!

Tái cơ cấu sớm nên được xử lý giống như tối ưu hóa sớm và vì lý do tương tự. Khi nó xuống đến nó, lỗi đến từ mã. Bạn càng mã hóa nhiều thì càng có nhiều lỗi. Nếu bạn có một đoạn mã (theo hiểu biết tốt nhất của bạn) không chứa bất kỳ lỗi nào, thì không có nơi nào để đi nhưng xuống dốc. Bạn có thể không giới thiệu bất kỳ điều gì, nhưng bạn chắc chắn sẽ không xảy ra nếu bạn không chạm vào nó! Bằng cách tái cấu trúc, làm rõ, sắp xếp lại, hoặc ngược lại với mã hiện đang làm việc như dự định, bạn đang làm cho mình (và chủ nhân của bạn) một sự bất đồng lớn bằng cách phát sinh một rủi ro được đảm bảo cho một khoản hoàn trả lý thuyết.

Nếu bạn đã ở trong đó vì một lý do khác, hãy tiếp tục và giúp bạn dễ dàng hơn hoặc bất cứ ai lang thang theo con đường đó sau bạn. Nhưng không bao giờ tái cấu trúc mã làm việc, ngay cả khi nó trông đẹp hơn sau đó.

3

Bạn có thể làm cho "nặng chức năng làm tổ" tốt hơn nhiều chỉ bằng cách định dạng lại, xếp hàng các bộ phận của mức độ làm tổ như nhau trên cùng một cột, ví dụ:

AndFinally (AndThenDoThis 
      (DoThis (strVar, 
         1, 
         DoThat("February"))), 
      FetchValue(0)) 

Bằng cách đó, "dọn dẹp" không thể gây ra lỗi (trừ khi cú pháp của ngôn ngữ của bạn nhạy cảm với khoảng trắng), và toàn bộ luồng của nó thực sự trở nên rõ ràng.

+0

Tôi đồng ý rằng loại thay đổi này sẽ không dẫn đến lỗi, nhưng tôi không quan tâm quá nhiều đến giao diện của nó. Đối với cá nhân tôi, nó thậm chí tệ hơn những gì chúng tôi bắt đầu. Tôi có lẽ sẽ giới thiệu các biến để lưu trữ các kết quả trung gian. – Mario

+0

Tệ hơn ??Bạn đang giỡn hả? – Svante

+0

Tôi thực hiện việc này thường xuyên. Cá nhân tôi ghét các biến tạm thời bởi vì chúng hầu như không thể tìm thấy tên tốt và thêm độ dài không cần thiết và tôi tìm thấy các hàm lồng nhau một cách hoàn hảo có thể đọc được nếu được định dạng đúng. – dsimcha

1

Làm đẹp nằm trong con mắt của khán giả.

Tôi chắc chắn có những người sẽ quét lại mã của bạn vì họ nghĩ rằng nó không đẹp. Bạn sẽ làm gì sau đó? Tái cấu trúc lại nó? Bạn sẽ kết thúc trong một vòng luẩn quẩn.

Vì vậy, hãy chống lại sự cám dỗ để mã refactor chỉ vì mã của bạn là đẹp hơn.

+0

Tôi nghĩ rằng loại điều này rất có thể xảy ra tại các cửa hàng CNTT. Đó là lý do tại sao tôi nghĩ rằng có một nhóm tiêu chuẩn liên tục xuất bản cho một tài liệu chuẩn là rất quan trọng. Việc áp dụng các tiêu chuẩn nên lý tưởng hạn chế chu trình. – Mario

3

Tôi đã có một đồng nghiệp (không còn với chúng tôi) liên tục 'cố định' mã xấu xí. Vấn đề là lúc nào anh ta đã phá vỡ nó, và lúc nào anh ta làm cho nó xấu xí theo cách khác. Một ngày một lớp học sẽ có một bàn tay đầy đủ các phương pháp 10 hoặc 20 dòng dài, ngày hôm sau nó sẽ có 30 phương pháp mỗi một hoặc hai dòng dài, và ít nhất một trong những hành vi lớp học sẽ bị phá sản.

Nếu aint bị hỏng thì không khắc phục được.

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