Câu trả lời:
Những người khác đã đề cập rằng một số cấu trúc nhất định như Collections
đối tượng yêu cầu và đối tượng có chi phí cao hơn so với các đối tác ban đầu của chúng (bộ nhớ và quyền anh).
Một xem xét khác là:
Có thể hữu ích khi khởi tạo Đối tượng null
hoặc gửi null
các tham số vào một phương thức / hàm tạo để chỉ ra trạng thái hoặc chức năng. Điều này không thể được thực hiện với nguyên thủy.
Nhiều lập trình viên khởi tạo các số thành 0 (mặc định) hoặc -1 để biểu thị điều này, nhưng tùy thuộc vào trường hợp, điều này có thể không chính xác hoặc gây hiểu lầm.
Điều này cũng sẽ thiết lập bối cảnh NullPointerException
khi một thứ gì đó được sử dụng không đúng cách, thân thiện với lập trình viên hơn nhiều so với một số lỗi tùy ý.
Nói chung, bạn nên sử dụng các kiểu nguyên thủy trừ khi bạn cần một đối tượng vì lý do nào đó (ví dụ: để đưa vào một bộ sưu tập). Thậm chí sau đó, hãy xem xét một cách tiếp cận khác không yêu cầu đối tượng nếu bạn muốn tối đa hóa hiệu suất số. Điều này được tư vấn bởi tài liệu và bài viết này trình bày cách tự động đấm bốc có thể gây ra sự khác biệt lớn về hiệu suất.
Integer
là dễ đọc hơn int
.
Theo ý kiến của tôi, nếu các thành viên trong lớp của tôi là biến trình bao bọc, thì nó không dựa trên các giá trị mặc định, đó là hành vi thân thiện với nhà phát triển.
1.
class Person {
int SSN ; // gets initialized to zero by default
}
2.
class PersonBetter {
Integer SSN; //gets initialized to null by default
}
Trong trường hợp đầu tiên, bạn không thể giữ giá trị SSN chưa khởi tạo. Nó có thể bị tổn thương nếu bạn không kiểm tra xem giá trị đã được đặt trước khi bạn cố gắng sử dụng nó hay chưa.
Trong trường hợp thứ hai, bạn có thể giữ SSN được khởi tạo bằng null. Điều này có thể dẫn đến NullPointerException nhưng tốt hơn là vô tình chèn các giá trị mặc định (không) dưới dạng SSN vào cơ sở dữ liệu bất cứ khi nào bạn cố gắng sử dụng nó mà không khởi tạo trường SSN.
PersonBuilder
ngoại lệ nếu SSN không được đặt trước khi gọi "build" để lấy Person
phiên bản. Tôi nghĩ điều này là quá đáng, nhưng đó là điều mà ngôn ngữ Java thúc đẩy để tạo ra các mẫu phù hợp.
Tôi sẽ chỉ sử dụng các loại trình bao bọc nếu bạn phải.
Khi sử dụng chúng, bạn không thu được nhiều, ngoài thực tế là chúng đang có Objects
.
Và, bạn mất chi phí sử dụng bộ nhớ và thời gian dành cho quyền anh / mở hộp.
Thực tế, tôi đã gặp một tình huống mà việc sử dụng lớp wrapper có thể được giải thích.
Tôi đã tạo một lớp dịch vụ có một long
biến kiểu
long
- khi không được khởi tạo, nó sẽ được đặt thành 0 - điều này sẽ gây nhầm lẫn cho người dùng khi hiển thị trong GUI Long
- khi không được khởi tạo, nó sẽ được đặt thành null
- giá trị null này sẽ không hiển thị trong GUI.Điều này cũng áp dụng cho Boolean
những nơi giá trị có thể gây nhầm lẫn hơn khi chúng ta sử dụng nguyên thủy boolean
(vì giá trị mặc định là sai).
Các tập hợp là trường hợp điển hình cho các đối tượng trình bao bọc Java đơn giản. Tuy nhiên, bạn có thể cân nhắc việc cung cấp cho Wrapper một ý nghĩa cụ thể hơn trong mã (đối tượng giá trị).
IMHO hầu như luôn luôn có lợi khi sử dụng các đối tượng giá trị khi nó tóm tắt về khả năng đọc và duy trì mã. Việc bao bọc các cấu trúc dữ liệu đơn giản bên trong các đối tượng khi chúng có những trách nhiệm nhất định thường đơn giản hóa mã. Đây là điều rất quan trọng trong Thiết kế theo hướng miền .
Tất nhiên là có vấn đề về hiệu suất, nhưng tôi có xu hướng bỏ qua điều đó cho đến khi tôi có khả năng đo lường hiệu suất với dữ liệu thích hợp và thực hiện các hành động trực tiếp hơn đối với khu vực có vấn đề. Nó cũng có thể dễ hiểu hơn về vấn đề hiệu suất nếu mã cũng dễ hiểu.
hiệu suất của các ứng dụng bị chi phối bởi các tính toán số có thể được hưởng lợi rất nhiều từ việc sử dụng các nguyên thủy.
kiểu nguyên thủy, người ta sử dụng toán tử ==, nhưng đối với trình bao bọc, lựa chọn ưu tiên là gọi phương thức equals ().
"Các kiểu nguyên thủy được coi là có hại" vì chúng trộn lẫn "ngữ nghĩa thủ tục vào một mô hình hướng đối tượng thống nhất khác.
Nhiều lập trình viên khởi tạo các số thành 0 (mặc định) hoặc -1 để biểu thị điều này, nhưng tùy thuộc vào trường hợp, điều này có thể không chính xác hoặc gây hiểu lầm.
Nếu bạn muốn sử dụng Bộ sưu tập, bạn phải sử dụng các lớp Wrapper.
Các kiểu nguyên thủy, được sử dụng cho các mảng. Ngoài ra, để đại diện cho dữ liệu không có hành vi, ví dụ: bộ đếm hoặc điều kiện boolean.
Kể từ khi autoboxing, biên giới "khi nào sử dụng nguyên thủy hoặc trình bao bọc" đã trở nên khá mờ nhạt.
Nhưng hãy nhớ rằng, Wrappers là các đối tượng, vì vậy bạn sẽ có được tất cả các tính năng Java ưa thích. Ví dụ: bạn có thể sử dụng phản xạ để tạo các đối tượng Số nguyên, nhưng không sử dụng giá trị int. Các lớp gói cũng có các phương thức như valueOf.
Nếu bạn muốn tạo một loại giá trị. Một cái gì đó như ProductSKU hoặc AirportCode.
Khi một kiểu nguyên thủy (chuỗi trong các ví dụ của tôi) xác định bình đẳng, bạn sẽ muốn ghi đè bình đẳng.
Các giá trị nguyên thủy trong Java không phải là đối tượng. Để thao tác các giá trị này với tư cách là đối tượng, gói java.lang cung cấp một lớp trình bao bọc cho mỗi kiểu dữ liệu nguyên thủy.
Tất cả các lớp Wrapper là cuối cùng. Đối tượng của tất cả các lớp trình bao bọc có thể được khởi tạo là bất biến có nghĩa là không thể thay đổi giá trị trong đối tượng trình bao bọc.
Mặc dù, lớp void được coi là một lớp bao bọc nhưng nó không bọc bất kỳ giá trị nguyên thủy nào và không thể khởi tạo. Nó không có hàm tạo công khai, nó chỉ biểu thị một đối tượng lớp đại diện cho từ khóa void.