Khi nào cần cấu trúc lại


32

Tôi đã đọc qua hầu hết cuốn sách Tái cấu trúc của Fowler và đã tái cấu trúc nhiều ứng dụng trong quá khứ lớn nhỏ của tôi.

Một trong những điều khó hơn tôi tìm thấy để dạy là "khi nào" để tái cấu trúc. Tôi có xu hướng làm điều này dựa trên cảm giác ruột thịt đã phục vụ tôi rất tốt trong quá khứ. Tuy nhiên, khi tham gia thảo luận với mọi người về việc liệu một đoạn mã nên được để lại một mình hay tái cấu trúc ngay bây giờ, thật khó để đứng trước "kiểm tra ruột".

Tôi cảm thấy nên có những cách tiếp cận khắt khe hơn về vấn đề này, nhưng không chắc chúng là gì.

Tôi hiểu "mùi mã", tái cấu trúc màu đỏ và các suy nghĩ khác, nhưng tôi thường cảm thấy rằng thời điểm tốt nhất để tái cấu trúc không phải là lần đầu tiên bạn viết mã, mà là lần thứ hai hoặc thứ ba bạn sử dụng mã và nhận ra rằng nó thực sự là một vấn đề và đang được sử dụng thực tế.


2
Về cơ bản, bạn đang hỏi điều tương tự như thế này: lập trình viên.stackexchange.com / questions / 6268 / Fiêu . Ngoại trừ ngưỡng của bạn để thực hiện hành động thấp hơn, vì chi phí và rủi ro thấp hơn, phải không?
S.Lott

Câu trả lời:


22

Refactor khi chi phí của refactoring là ít hơn chi phí của không refactoring.

Đo lường "chi phí" tuy nhiên bạn có thể. Ví dụ, mã được triển khai kém đến mức các lỗi tầm thường tốn hàng giờ hoặc hàng ngày để sửa chữa? Tái cấu trúc sẽ cho phép bạn có được nhiều khách hàng hơn, hoặc tăng công suất, hoặc cải thiện hiệu suất và do đó làm cho khách hàng hiện tại của bạn hạnh phúc hơn?



8
Nói cách khác: "đáng để tái cấu trúc khi đáng để tái cấu trúc". Duh. Chà, nó không thực sự là một câu trả lời, phải không :) Measure "cost" however you can.- OK, thế nào? Đó không phải là ý chính của câu hỏi sao? Quan điểm thời gian nào nên được áp dụng khi đo lường chi phí đó?
Konrad Morawski

2
@Morawski: không, Đó là một cách diễn đạt không chính xác. Tôi đã nói rằng nó đáng để tái cấu trúc nếu giá trị nhận được từ tái cấu trúc lớn hơn chi phí tái cấu trúc. Điều đó không giống như nói rằng "nó đáng để tái cấu trúc khi nó đáng để tái cấu trúc". Tính chi phí tái cấu trúc. Tính chi phí không tái cấu trúc. Cái nào to hơn?
Bryan Oakley

@BryanOakley: vấn đề là, bạn không thể "tính toán" các chi phí này. Bạn có thể ước tính tốt nhất chúng, điều này thực sự khó thực hiện khi nói đến chi phí không tái cấu trúc . Bộ nhân chi phí bảo trì nào bạn áp dụng cho phiên bản chưa được tái cấu trúc so với phiên bản tái cấu trúc? Làm thế nào để bạn biết nếu mã trong câu hỏi sẽ phải được duy trì hoặc thay đổi ở tất cả? Làm thế nào để bạn ước tính số lượng lỗi nó sẽ tạo ra? Cuối cùng, tôi đoán rằng tất cả chúng ta đều vô thức đưa ra những loại ước tính này như là một phần của quá trình quyết định của chúng ta khi chúng ta nghĩ về tái cấu trúc, nhưng không có sự chính xác nào được mong đợi từ nó.
guillaume31

1
@ ian31: đúng, bạn không thể tính toán các giá trị và điều tốt nhất bạn có thể làm là ước tính. Tuy nhiên, đây là cách thực sự hợp lệ duy nhất để quyết định có nên cấu trúc lại hay không, giả sử bạn có giới hạn thời gian và nguồn lực. Bạn cần phải quyết định xem liệu refactor có xứng đáng hay không. Làm thế nào bạn xác định "giá trị" là một khoa học rất không chính xác. Vấn đề là, bạn không nên cấu trúc lại cảm giác ruột - nên có một lý do chính đáng để thực hiện tái cấu trúc ngoài "tôi muốn mã đẹp hơn".
Bryan Oakley

12

  1. độ phức tạp chu kỳ của hàm dưới 5?
  2. Bạn đã hoàn toàn hiểu sự phức tạp chu kỳ là gì mà không theo liên kết đó?
  3. Bạn có kiểm tra tự động hoặc trường hợp kiểm tra tài liệu cho mọi đường dẫn thông qua chức năng không?
  4. Có phải tất cả các trường hợp thử nghiệm hiện có vượt qua?
  5. Bạn có thể giải thích chức năng và tất cả các trường hợp cạnh của nó trong vòng chưa đầy 1 phút không?
  6. Nếu không thì khoảng 5 phút?
  7. 10 phút?
  8. Có ít hơn 100 dòng mã trong hàm (bao gồm cả nhận xét) không?
  9. Bạn có thể tìm thấy hai nhà phát triển khác đồng ý mã này không có lỗi chỉ bằng cách kiểm tra trực quan?
  10. Là chức năng này được sử dụng ở một nơi duy nhất?
  11. Chức năng có đáp ứng mục tiêu hiệu suất của nó (Thời gian / Bộ nhớ / CPU) không?

Chấm điểm

Thêm câu trả lời "không" ở trên:

  • 0-1 - Tại sao bạn thậm chí sẽ nghĩ về việc tái cấu trúc này? Bạn có thể chỉ muốn đổi tên các biến vì bạn không thích quy ước đặt tên của nhà phát triển trước đó
  • 2-5 - Điều này có thể cần một chút điều chỉnh, nhưng tôi sẽ không giữ bản phát hành sản xuất cho thứ gì đó trong phạm vi này
  • 6-8 - OK, có lẽ chúng ta cần khắc phục điều này ... Có khả năng chúng ta sẽ tiếp tục xem lại điều này và / hoặc chúng ta không thực sự biết nó đang làm gì. Vẫn còn trên hàng rào, nhưng nó rất đáng ngờ
  • 9+ - Đây là một ứng cử viên chính cho tái cấu trúc. (Lưu ý, viết test case là một hình thức tái cấu trúc)

http://mikemainguy.blogspot.com/2013/05/when-to-refactor-code.html


4
# 2 nghe có vẻ rất hợm hĩnh và thực sự vô dụng để đánh giá mã . # 3 & # 4 không phải mọi công ty đều sử dụng các bài kiểm tra đơn vị. # 8 Tránh bình luận bất cứ khi nào có thể, và 100 dòng là quá cao. Tôi có 1 màn hình rộng lớn ở chế độ dọc và tôi hầu như không thể nhìn thấy toàn bộ chức năng cùng một lúc. Nếu đó là hơn 15 dòng mã thực tế, thì đã có một lý do chắc chắn tại sao bạn giữ nó như vậy. Đó là một cách tiếp cận thực tế, tốt đẹp để có một danh sách kiểm tra, nhưng quá nhiều điểm ở đây chỉ được tạo thành hoặc sử dụng các giá trị ngẫu nhiên mà không có bất kỳ lý do nào đằng sau nó.
R. Schmitz

8

Khi chú ruột của bạn nói với bạn rằng có lẽ bạn nên thực hiện một số phép tái cấu trúc, có khả năng đó là bản năng của bạn nói với bạn một chút muộn màng rằng bạn đã bỏ qua một điều gì đó quan trọng quá lâu.

Tôi hiểu "mùi mã", tái cấu trúc màu đỏ và các suy nghĩ khác, nhưng tôi thường cảm thấy rằng thời điểm tốt nhất để tái cấu trúc không phải là lần đầu tiên bạn viết mã, mà là lần thứ hai hoặc thứ ba bạn sử dụng mã và nhận ra rằng nó thực sự là một vấn đề và đang được sử dụng thực tế.

Có hiệu quả hai cấp độ để tái cấu trúc. Đầu tiên là các vấn đề rõ ràng xuất hiện khi bạn mã đầu tiên. Đây là những tối ưu hóa nhỏ mà chi phí bạn rất ít để làm trước. Những thứ như giữ cho các phương thức và lớp của bạn nhỏ, và tuân thủ DRY và SRP. Sau đó, bạn có giai đoạn bổ sung đối phó với lỗ hổng lớn trong thiết kế của bạn, mà có thể không ngay lập tức rõ ràng cho đến khi mã của bạn có một vài dặm dưới nó. Đây là cấp độ thứ hai mà bạn đang nói đến, nhưng để đảm bảo rằng việc tái cấu trúc sau này không quá tốn kém, bạn cần phải viết mã của mình theo cách mà nỗ lực mà bạn dự tính được thực hiện dễ dàng hơn và ít tốn kém hơn, có nghĩa là thực hiện tái cấu trúc sớm.

Như Jeff đã đề cập trong câu trả lời của mình, "thời gian là tiền bạc" , đặc biệt là trong các công ty nơi khối lượng công việc cao và rủi ro thậm chí còn cao hơn. Thời gian sử dụng trước để đảm bảo mã ở trạng thái tốt nhất có thể là thời gian được lưu sau đó, khi trêu chọc những gì đáng lẽ phải là một phép tái cấu trúc dễ dàng hóa ra lại là một hoạt động chính.

Khi viết phần mềm, mọi khoảnh khắc dành cho việc cải thiện mã của bạn lên trước là thời gian được lưu lại sau đó, khi bạn thực sự sẽ cần nó. Bạn tái cấu trúc càng sớm, những thay đổi sau này của bạn sẽ càng rõ ràng. Nó giống như thực hiện một khoản thanh toán bằng đô la ngày nay so với các khoản nợ kỹ thuật trong tương lai sẽ có trong ngày mai tăng vọt.

Trong mọi trường hợp, tái cấu trúc không phải là một nhiệm vụ mà bạn đặt ra cho đến một tương lai bí ẩn nào đó khi phần mềm đã hoàn tất và ổn định, vì nó làm tăng rủi ro của bạn sau này khi cổ phần cao hơn nhiều và sản phẩm khó thay đổi hơn nhiều. Tái cấu trúc nên là một phần trong các hoạt động hàng ngày của bạn và đây là bản chất của triết lý Red-Green-Refactor mà bạn đã đề cập.


2

Tôi nghĩ rằng câu hỏi của bạn có thể được trả lời khác nhau bởi mỗi nhà phát triển và thậm chí cả quản lý phụ trách lập trình.

Sở thích cá nhân của tôi là, bất cứ khi nào tôi học được điều gì đó mới hoặc cải thiện các thực tiễn tốt nhất của mình, tôi sẽ cấu trúc lại mã mà tôi có thể - Tôi muốn giữ mã của mình đạt tiêu chuẩn ngay khi tôi tìm hiểu tiêu chuẩn tốt nhất để sử dụng cho tình huống đó là gì. Tôi được phép làm điều này vì đây là một công ty nhỏ hơn sử dụng cùng một phần mềm trong thời gian dài.

Trong một công ty phát triển phần mềm lớn hơn, nơi thời gian là tiền bạc, có thể chỉ cần bắt đầu thiết kế với các thực tiễn tốt hơn mà bạn đã học được từ thời điểm này trở đi, đừng lo lắng về việc tái cấu trúc cho đến khi bản án 2 của phần mềm cụ thể đó?

Tôi cảm thấy việc giảng dạy khi nào để tái cấu trúc thực sự phụ thuộc vào công ty bạn hiện đang làm việc.


2

"Khi nào tái cấu trúc?"

Câu trả lời ngắn: mỗi khi bạn gặp mã có mùi khó chịu hoặc có thể được cải thiện ( Quy tắc hướng đạo của nam sinh )

Thực tế, điều này xảy ra:

  • Nếu bạn thực hành TDD, một cách có hệ thống trong bước Tái cấu trúc của chu trình TDD, nghĩa là, một khi bài kiểm tra của bạn có màu xanh và trước khi bạn bắt đầu viết một bài kiểm tra mới.
  • Là kết quả của việc xem xét mã
  • Khi tiếp quản mã kế thừa
  • Khi tiêu thụ mã có vẻ lúng túng được thiết kế
  • v.v.

Tôi cảm thấy như thế này chỉ nói "Bạn nên tái cấu trúc" mà không trả lời phần khó hơn: "Tôi cảm thấy như nên có những cách tiếp cận chặt chẽ hơn cho vấn đề này, nhưng không chắc chúng là gì."
Làm việc vào

Tôi không biết phải nói gì ngoại trừ cảm thấy đau đớn khi duy trì, ngửi mùi mã và sử dụng kinh nghiệm của bạn. Tôi nghi ngờ sẽ không bao giờ có một phương pháp xác định, được thiết lập để cho bạn biết khi nào và những gì cần cấu trúc lại nếu đó là những gì bạn đang tìm kiếm.
guillaume31

1

Khi tôi lần đầu tiên học về tái cấu trúc, người cố vấn của tôi đã nói với tôi: "Làm hai lần, giữ mũi. Làm ba lần. Tái cấu trúc." (Cảm ơn, Josh!) Để cụ thể, điều anh ta nói là khi bạn chuẩn bị viết cùng một khối mã lần thứ ba (hoặc thậm chí là một mẫu mã tương tự), đó là thời gian để cấu trúc lại. Tôi đã làm theo điều đó trong 10 năm qua, và thấy nó là một quy tắc đủ âm thanh.

Sử dụng Eclipse hoặc IDE tương tự có hỗ trợ tái cấu trúc mạnh mẽ, làm giảm nỗ lực thực hiện tái cấu trúc. Hỗ trợ IDE làm cho nhiều khả năng bạn sẽ tái cấu trúc ngay khi bạn đạt đến "lần thứ ba" (hoặc thấy sự cần thiết), thay vì xem đó là nỗ lực bổ sung.

Ngoài ra - TDD cũng là một trợ giúp lớn ở đây, vì bạn có thể tiếp tục chạy các bài kiểm tra của mình với tư cách là người tái cấu trúc và biết rằng bạn chưa làm hỏng bất cứ điều gì.


1

Tái cấu trúc theo định nghĩa của nó là một quá trình. Điều này ngụ ý rằng bạn không nên cố gắng tìm thời gian rảnh rỗi để thực hiện nhiệm vụ rafactoring, thay vào đó bạn nên tiếp tục tái cấu trúc mọi lúc khi bạn bắt gặp mã mã có thể được viết tốt hơn.

Cá nhân tôi thích viết các nguyên mẫu tiến hóa, nói đơn giản hơn: mã chỉ hoạt động và sau đó tái cấu trúc chúng cho đến khi chúng đáp ứng các tiêu chuẩn mã hóa dự kiến. Một ví dụ điển hình khác là thêm chức năng bổ sung và tái cấu trúc mã hiện có để cho phép tái sử dụng nó.


1

Trong 20 năm lập trình của tôi, đây là quy tắc duy nhất mà tôi thực sự thấy công việc, mà mọi người có thể gắn bó và các nhà quản lý cho phép thời gian. (Tái cấu trúc giống như ăn kiêng: chắc chắn, "lượng calo trong / calo ra" là công thức để giảm cân, nhưng điều đó không chuyển thành chế độ ăn kiêng mà mọi người sẽ tuân thủ.) Và như vậy:

Tái cấu trúc liên tục, khi bạn làm việc. Sử dụng Phát triển hướng thử nghiệm để bạn có một số chu kỳ tái cấu trúc màu đỏ-xanh trong suốt cả ngày. Tái cấu trúc chỉ các phần của mã mà bạn đã chạm vào.

Một khi bạn chắc chắn hơn về bản thân, bạn có thể thay đổi từ chế độ này.


1

Tôi nghĩ rằng, điều đó phụ thuộc vào yêu cầu của chủ dự án và anh chàng trả lời cho chất lượng của mã. Bạn chỉ đơn giản là không thể quyết định nó một mình, khi tiền của người khác đang bị nghi ngờ.

Vì lý do kỹ thuật, có một số.

  • Nếu bạn có một lỗi trong mã, điều đó có nghĩa là nơi này bị hiểu lầm và RẤT có thể có nhiều lỗi có thể bị ẩn ở đây và chắc chắn sẽ có vấn đề lớn với bất kỳ nỗ lực nào để phát triển các phần mã được kết nối. Vì vậy, nơi này nên được kiểm tra để tái cấu trúc có thể.
  • Một lý do khác là khi bạn thêm hoặc thay đổi một tính năng và mã cũ rất bất tiện cho việc thay đổi / thêm và các thay đổi / bổ sung sau này rất có thể. Tất nhiên, bạn nên cân đối chi phí.
  • Có thể lý do nghiêm trọng nhất là khi bạn thay đổi mã và điều đó là không thể.

Là một bậc thầy về scrum, chúng tôi có một nhà phát triển liên tục lập luận rằng mọi câu chuyện mà nhóm có quy mô lớn hơn những gì nhóm nghĩ và nhận ra rằng anh ta muốn cấu trúc lại mọi đoạn mã anh ta gặp. Do đó, một câu chuyện 3 điểm luôn là một số 8 đối với anh ta. Rõ ràng điều này đã làm hỏng việc cung cấp giá trị. Vì vậy, bằng cách nào đó cần phải có một số hiểu biết về khi nào nên cấu trúc lại, và quyết định nên được đưa ra như thế nào. Chỉ là suy nghĩ của tôi, từ kinh nghiệm đó (và một vài thứ khác).
Curtis Reed
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.