2011-07-21 32 views
46

Trong cuốn sách "hiệu quả Java", Josh Bloch nói rằngStringBuffer đã lỗi thời?

StringBuffer phần lớn là lỗi thời và cần được thay thế bằng không đồng bộ thực hiện 'StringBuilder'

.

Nhưng theo kinh nghiệm của tôi, tôi vẫn thấy việc sử dụng rộng rãi lớp StringBuffer. Tại sao lớp StringBuffer bây giờ đã lỗi thời và tại sao StringBuilder nên được ưu tiên hơn StringBuffer ngoại trừ hiệu suất tăng lên do không đồng bộ hóa?

+7

Bạn thấy StringBuffer được sử dụng rộng rãi vì cùng lý do bạn vẫn thấy lớp Vector được sử dụng rộng rãi, tức là 1. mọi người đọc sách trước Java 1.5. 2. bạn vẫn tìm thấy rất nhiều ví dụ trên Net sử dụng StringBuffer. 3. vẫn có những người ngoài chương trình/dạy Java nhưng không biết về StringBuilder. – helpermethod

Trả lời

65

Đó là lỗi thời trong đó mã mới trên Java 1.5 thường nên sử dụng StringBuilder - đó là rất hiếm hoi mà bạn thực sự cần để xây dựng chuỗi một cách thread-safe, vậy tại sao thanh toán chi phí đồng bộ hóa?

tôi nghi ngờ mã mà bạn thấy sử dụng StringBuffer chủ yếu rơi vào xô:

  • Viết trước Java 1.5
  • Viết để duy trì khả năng tương thích với JDK cũ
  • Viết bởi những người không biết về StringBuilder
  • Được tạo bằng công cụ không biết về StringBuilder
+20

Tôi đã đi qua mã của StringBuffer và StringBuilder. Chúng giống hệt nhau ngoại trừ tất cả các phương thức của StringBuffer được nối với từ khóa được đồng bộ hóa. –

+0

@Varun: Điều đó sẽ không làm tôi ngạc nhiên chút nào. –

+0

Tôi nghi ngờ rằng rất nhiều người biết về StringBuilder tiếp tục sử dụng StringBuffer trong thói quen tuyệt đối. Tôi biết tôi phải chiến đấu với nó ... –

18

Không phải ai cũng đọc rộng rãi như bạn :-)

Tôi chỉ nói đùa một nửa. Mọi người sao chép mã và mẫu mọi lúc. Nhiều người không giữ liên lạc với các thay đổi về API.

Tại sao StringBuffer lỗi thời? Bởi vì trong phần lớn các trường hợp, hành vi đồng bộ của nó là không cần thiết. Tôi không thể nghĩ ra một khoảng thời gian tôi cần nó. Mặc dù thực tế là đồng bộ hóa không phải là vấn đề hiệu suất mà nó từng là, nó làm cho ít ý nghĩa để trả thuế trong các tình huống mà nó không cần thiết.

9

Tại sao lớp StringBuffer giờ đã lỗi thời?

Vì các hoạt động của nó được đồng bộ hóa, làm tăng thêm chi phí và hiếm khi hữu ích.

Lý do tại sao bạn vẫn thấy StringBuffer sử dụng rộng rãi chỉ đơn giản là quán tính: Hiện vẫn còn vô số ví dụ mã hướng dẫn ra khỏi đó mà không bao giờ được cập nhật để sử dụng StringBuilder, và mọi người vẫn học tập quán lạc hậu (không chỉ một này) từ các nguồn như vậy. Và ngay cả những người biết tốt hơn thường rơi trở lại thói quen cũ.

4

Không chỉ đồng bộ hóa trong hầu hết các trường hợp, nó thực sự cung cấp cho người đọc thông tin sai mã của bạn nếu bạn vẫn sử dụng nó: cụ thể là người đọc có thể được tin rằng yêu cầu đồng bộ hóa là không thực sự.

Sử dụng số StringBuilder thay vì quảng cáo thực tế là bạn không mong đợi quyền truy cập qua luồng.

Thực tế, việc gửi dữ liệu qua các luồng hầu như luôn luôn được thực hiện thông qua các kênh truyền thông được xác định rõ, không chỉ đơn giản bằng cách truy cập bộ đệm chuỗi được đồng bộ hóa. Vì vậy, theo cách tôi khuyên bạn nên luôn luôn bằng cách sử dụng một giải pháp khác, ngay cả khi một số StringBuffer có vẻ phù hợp ngay từ cái nhìn đầu tiên.

5

Tôi nghĩ rằng lỗi thời là một sự nói quá.

StringBuffer được đồng bộ hóa. StringBuilder thì không.

Trong nhiều trường hợp (có thể là hầu hết), bạn sẽ không quan tâm đến độ an toàn của chuỗi được sử dụng để tạo chuỗi. Bạn nên sử dụng StringBuilder trong những trường hợp này. Tuy nhiên, trong một số trường hợp, bạn có thể rất muốn đảm bảo hành động trên đối tượng là an toàn. StringBuffer vẫn hữu ích trong những trường hợp này.

+3

Không chắc chắn tôi có thể nghĩ ra một lý do chính đáng để có nhiều chủ đề xây dựng một chuỗi, nếu bạn quan tâm đến thứ tự của dữ liệu trong chuỗi kết quả. – Hardwareguy

+2

@ Hardwareguy: Một số loại logger tôi giả sử, vì bạn có thể làm việc bằng cách nối thêm toàn bộ thông điệp. Mặc dù vậy sẽ rất lộn xộn và có Mã Mùi kém. –

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