Công cụ để chuyển đổi mã Python để tuân thủ PEP8


113

Tôi biết có những công cụ xác thực xem mã Python của bạn có tuân thủ PEP8 hay không, ví dụ: có cả dịch vụ trực tuyếnmô-đun python .

Tuy nhiên, tôi không thể tìm thấy một dịch vụ hoặc mô-đun có thể chuyển đổi tệp Python của tôi thành tệp Python hợp lệ PEP8 độc lập. Có ai biết nếu có bất kỳ?
Tôi cho rằng nó khả thi vì PEP8 là tất cả về sự xuất hiện của mã, phải không?


1
Tôi không nghĩ rằng có bất kỳ công cụ nào chuyển đổi mã sang mã tương thích PEP8. PEP8 cũng bao gồm các quy tắc đặt tên biến, vì vậy, nếu công cụ như vậy tồn tại thì nó cũng sẽ đổi tên các tên biến của bạn và khi đó bạn có thể không hiểu được mã của chính mình.
Ashwini Chaudhary

1
@AshwiniChaudhary Đó là một điểm tốt, cũng cần nhắc lại rằng việc thay đổi tên biến có thể ảnh hưởng đến những người khác đã sử dụng mã của bạn, vì vậy không phải lúc nào cũng là một ý kiến ​​hay. (autopep8 không làm điều này.)
Andy Hayden

Câu trả lời:


38

Thật không may "pep8 gây bão" (toàn bộ dự án) có một số tác dụng phụ tiêu cực:

  • rất nhiều xung đột hợp nhất
  • đổ lỗi cho git
  • làm cho việc xem xét mã khó khăn

Như một sự thay thế (và cảm ơn @yp vì ý tưởng ), tôi đã viết một gói nhỏ autopep8s chỉ những dòng mà bạn đã làm việc kể từ lần cam kết / nhánh cuối cùng:

Về cơ bản, việc rời khỏi dự án tốt hơn một chút so với những gì bạn thấy :

pip install pep8radius

Giả sử bạn đã hoàn thành công việc của mình mastervà sẵn sàng cam kết:

# be somewhere in your project directory
# see the diff with pep, see the changes you've made since master
pep8radius master --diff
# make those changes
pep8radius master --diff --in-place

Hoặc để xóa các dòng mới mà bạn đã cam kết kể từ lần cam kết cuối cùng:

pep8radius --diff
pep8radius --diff --in-place

# the lines which changed since a specific commit `git diff 98f51f`
pep8radius 98f51f --diff

Về cơ bản pep8radiuslà áp dụng autopep8 cho các dòng trong đầu ra của git / hg diff (từ cam kết được chia sẻ cuối cùng ).

Script này hiện hoạt động với git và hg, nếu bạn đang sử dụng thứ gì đó khác và muốn nó hoạt động, vui lòng gửi bình luận / issue / PR !


2
1 sáng kiến rất tốt ... tôi đang suy nghĩ về làm thế nào để làm cho một Notepad ++ plugin cho cùng một mục đích ... vì đó là biên tập viên của tôi yêu thích trên Windows
kmonsoor

1
@kmonsoor ý kiến ​​hay, tôi chưa nghĩ về plugin trình chỉnh sửa! Hãy cho tôi biết trên github bất kỳ cách nào tôi có thể giúp đỡ / giúp dễ sử dụng hơn bên ngoài CLI ... Tôi nhận thấy một vài vấn đề (có thể giải quyết).
Andy Hayden

ở đây tôi đã tìm thấy một danh sách thú vị gồm các plugin trình chỉnh sửa github.com/jcrocholl/pep8/wiki/RelatedTools , mặc dù không may mắn cho Notepad ++ ...
kmonsoor

1
tôi vừa tạo một tập lệnh để làm cầu nối giữa Notepad ++ và Autopep8, dựa trên một plugin khác "Python Script". Tuy nhiên, nó hoạt động. Vui lòng kiểm tra tại đây: bit.ly/pep8_tonizer
kmonsoor

184

Bạn có thể sử dụng autopep8 ! Trong khi bạn pha cho mình một tách cà phê, công cụ này vui vẻ loại bỏ tất cả những vi phạm PEP8 khó chịu mà không làm thay đổi ý nghĩa của mã.

Cài đặt nó qua pip:

pip install autopep8

Áp dụng điều này cho một tệp cụ thể:

autopep8 py_file --in-place

hoặc đối với dự án của bạn (đệ quy), tùy chọn dài dòng cung cấp cho bạn một số phản hồi về cách nó diễn ra :

autopep8 project_dir --recursive --in-place --pep8-passes 2000 --verbose

Lưu ý: Đôi khi, mặc định 100 lần vượt qua là không đủ, tôi đặt nó thành 2000 vì nó cao hợp lý và sẽ bắt tất cả trừ các tệp rắc rối nhất (nó ngừng truyền khi không tìm thấy lỗi pep8 có thể giải quyết) ...

Tại thời điểm này, tôi khuyên bạn nên kiểm tra lại và thực hiện cam kết!

Nếu bạn muốn tuân thủ PEP8 "đầy đủ" : một chiến thuật tôi đã sử dụng là chạy autopep8 như trên, sau đó chạy PEP8, sẽ in các lỗi vi phạm còn lại (tệp, số dòng và nội dung):

pep8 project_dir --ignore=E501

và thay đổi từng cái một theo cách thủ công (ví dụ: E712s - so sánh với boolean).

Lưu ý: autopep8 đưa ra một --aggressiveđối số (để "sửa chữa" những vi phạm thay đổi ý nghĩa này một cách tàn nhẫn), nhưng hãy cẩn thận nếu bạn sử dụng hung hăng, bạn có thể phải gỡ lỗi ... (ví dụ: trong numpy / pandas True == np.bool_(True)nhưng không True is np.bool_(True)!)

Bạn có thể kiểm tra xem có bao nhiêu vi phạm của từng loại (trước và sau):

pep8 --quiet --statistics .

Lưu ý: Tôi coi E501s (dòng quá dài) là một trường hợp đặc biệt vì có thể sẽ có rất nhiều trong số này trong mã của bạn và đôi khi chúng không được autopep8 sửa chữa.

Ví dụ, tôi đã áp dụng kỹ thuật này cho cơ sở mã gấu trúc .


@hayden Bạn có nhận xét gì về mức độ đáng tin cậy của điều này và tỷ lệ các bản sửa lỗi tự động đối với các vấn đề kỳ lạ mà nó giới thiệu?
Marius

@Marius Tôi đã sử dụng điều này trên mã gấu trúc (khá lớn) và nó không hiển thị bất kỳ vấn đề kỳ lạ nào, nó sẽ không thay đổi mã làm thay đổi ý nghĩa , tôi đã cập nhật câu trả lời của mình để đề cập đến những điều này. Trước đây nó đã gặp sự cố với hashbang của Sphinx (một lỗi trong PEP8 hiện đã được khắc phục).
Andy Hayden

2
Điều này có thực thi Strunk và White trong các bình luận không?
Eric

1
Kể từ ngày 25 tháng 10 năm 2017, pep8gói được đề cập trong câu trả lời này đã được đổi tên thành pycodestyle: github.com/PyCQA/pycodestyle/releases/tag/1.7.1
hb20007

8

@Andy Hayden đã trình bày tổng quan tốt về autopep8. Thêm vào đó, có một gói nữa được gọi là pep8ify cũng thực hiện điều tương tự.

Tuy nhiên, cả hai gói chỉ có thể loại bỏ các lỗi xơ vải nhưng chúng không thể định dạng mã.

little = more[3:   5]

Đoạn mã trên vẫn giữ nguyên sau khi pep8zing. Nhưng mã có vẻ chưa tốt. Bạn có thể sử dụng các định dạng như yapf , sẽ định dạng mã ngay cả khi mã tuân thủ PEP8. Đoạn mã trên sẽ được định dạng thành

little = more[3:5]

Đôi khi điều này thậm chí phá hủy định dạng thủ công của bạn. Ví dụ

BAZ = {
    [1, 2, 3, 4],
    [5, 6, 7, 8],
    [9, 10, 11, 12]
}

sẽ được chuyển đổi thành

BAZ = {[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12]}

Nhưng Bạn có thể bảo nó bỏ qua một số phần.

BAZ = {
   [1, 2, 3, 4],
   [5, 6, 7, 8],
   [9, 10, 11, 12]
}  # yapf: disable

Lấy từ bài đăng trên blog cũ của tôi: Tự động PEP8 & Định dạng mã Python của bạn!


2
Có phải little = more[3: 5]lỗi trong pep8 (thư viện) không? yapf chắc chắn là tương lai ở đây, thuật toán đằng sau nó (về cơ bản là một đường đi ngắn nhất trong biểu đồ của tất cả các tùy chọn định dạng) là một giải pháp rất thanh lịch và có thể sẽ có ít lỗi hơn cũng như định dạng chuẩn.
Andy Hayden

@AndyHayden Có vẻ như đó là một tính năng bị thiếu, nó không khắc phục được E225
ChillarAnand

5

Nếu đang sử dụng eclipse + PyDev, bạn chỉ cần kích hoạt autopep8 từ cài đặt của PyDev: Windows -> Preferences -> gõ 'autopep8' vào bộ lọc tìm kiếm.

Kiểm tra "sử dụng autopep8.py để định dạng mã?" -> OK

Giờ đây, định dạng mã CTRL-SHIFT-F của eclipse sẽ định dạng mã của bạn bằng autopep8 :)

ảnh chụp màn hình


3

Tôi đã thực hiện nghiên cứu rộng rãi về các công cụ khác nhau cho phong cách python và mã. Có hai loại công cụ: linters - phân tích mã của bạn và đưa ra một số cảnh báo về các kiểu mã được sử dụng kém và hiển thị lời khuyên về cách khắc phục nó và bộ định dạng mã - khi bạn lưu tệp, nó sẽ định dạng lại tài liệu của bạn bằng kiểu PEP.

Bởi vì định dạng lại phải chính xác hơn - nếu nó tái tạo lại thứ gì đó mà bạn không muốn thì nó trở nên vô dụng - chúng che phủ ít phần của PEP hơn, xơ vải hiển thị nhiều hơn.

Tất cả chúng đều có các quyền khác nhau để định cấu hình - ví dụ, có thể định cấu hình pylinter trong tất cả các quy tắc của nó (bạn có thể bật / tắt mọi loại cảnh báo), màu đen hoàn toàn không thể định cấu hình.

Dưới đây là một số liên kết và hướng dẫn hữu ích:

Tài liệu:

Linters (theo thứ tự phổ biến):

Bộ định dạng mã (theo thứ tự phổ biến):


1

Có nhiều.

Các IDE thường có một số khả năng định dạng được tích hợp sẵn. IntelliJ Idea / PyCharm cũng vậy, tương tự với plugin Python cho Eclipse, v.v.

Có những định dạng / linters có thể nhắm mục tiêu nhiều ngôn ngữ. https://coala.io là một ví dụ điển hình cho những điều đó.

Sau đó, có các công cụ mục đích duy nhất, trong số đó nhiều công cụ được đề cập trong các câu trả lời khác.

Một phương pháp cụ thể để định dạng lại tự động là phân tích cú pháp tệp thành cây AST (không bỏ nhận xét) và sau đó kết xuất nó trở lại văn bản (có nghĩa là không có gì của định dạng ban đầu được giữ nguyên). Ví dụ về điều đó sẽ là https://github.com/python/black .

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.