null
Sử dụng là ứng dụng / ngôn ngữ phụ thuộc
Cuối cùng, việc lựa chọn sử dụng hay không null
làm giá trị ứng dụng hợp lệ phần lớn được quyết định bởi ứng dụng và ngôn ngữ / giao diện / cạnh lập trình của bạn.
Ở cấp độ cơ bản, tôi khuyên bạn nên thử sử dụng các loại riêng biệt nếu có các loại giá trị riêng biệt. null
có thể là một tùy chọn nếu giao diện của bạn cho phép và chỉ có hai loại tài sản bạn đang cố gắng đại diện. Bỏ qua một thuộc tính có thể là một tùy chọn nếu giao diện hoặc định dạng của bạn cho phép nó. Một loại tổng hợp mới (lớp, đối tượng, loại thông báo) có thể là một tùy chọn khác.
Đối với ví dụ chuỗi của bạn, nếu đây là ngôn ngữ lập trình, tôi sẽ tự hỏi mình một vài câu hỏi.
- Tôi có kế hoạch thêm các loại giá trị trong tương lai không? Nếu vậy,
Option
có lẽ sẽ tốt hơn cho thiết kế giao diện của bạn.
- Khi nào tôi cần xác thực các cuộc gọi của người tiêu dùng? Tĩnh? Năng động? Trước? Sau? Ở tất cả? Nếu ngôn ngữ lập trình của bạn hỗ trợ nó, hãy sử dụng các lợi ích của việc gõ tĩnh vì nó tránh được số lượng mã bạn phải tạo để xác thực.
Option
có thể lấp đầy trường hợp này tốt nhất nếu chuỗi của bạn không thể rỗng. Tuy nhiên, null
dù sao đi nữa , bạn có thể sẽ phải kiểm tra đầu vào của người dùng để biết giá trị chuỗi, vì vậy tôi có thể hoãn lại câu hỏi đầu tiên: tôi muốn đại diện cho bao nhiêu loại giá trị.
- Là
null
dấu hiệu của một lỗi lập trình viên trong ngôn ngữ lập trình của tôi? Thật không may, null
thường là giá trị mặc định cho các con trỏ hoặc tham chiếu chưa được khởi tạo (hoặc không được khởi tạo rõ ràng) trong một số ngôn ngữ. Là null
một giá trị được chấp nhận như giá trị mặc định? Có an toàn như một giá trị mặc định? Đôi khi null
là biểu thị của các giá trị được giải quyết. Tôi có nên cung cấp cho người tiêu dùng giao diện của mình một dấu hiệu về các vấn đề khởi tạo hoặc quản lý bộ nhớ tiềm năng này trong chương trình của họ không? Chế độ thất bại của một cuộc gọi như vậy khi đối mặt với những vấn đề như vậy là gì? Là người gọi trong cùng một quy trình hoặc chủ đề như của tôi để các lỗi như vậy có nguy cơ cao đối với ứng dụng của tôi?
Tùy thuộc vào câu trả lời của bạn cho những câu hỏi này, có lẽ bạn sẽ có thể trau dồi xem liệu có null
phù hợp với giao diện của bạn hay không .
ví dụ 1
- Ứng dụng của bạn rất quan trọng
- Bạn đang sử dụng một số loại khởi tạo heap khi khởi động và
null
là giá trị chuỗi có thể được truyền lại khi không thể phân bổ không gian cho chuỗi.
- Có một tiềm năng như một chuỗi đánh vào giao diện của bạn
Trả lời: null
có lẽ không phù hợp
Đặt vấn đề: null
trong trường hợp này thực sự được sử dụng để chỉ ra hai loại giá trị khác nhau. Giá trị đầu tiên có thể là giá trị mặc định mà người dùng giao diện của bạn có thể muốn đặt. Thật không may, giá trị thứ hai là một lá cờ để chỉ ra rằng hệ thống của bạn không hoạt động chính xác. Trong những trường hợp như vậy, bạn có thể muốn thất bại một cách an toàn nhất có thể (bất cứ điều gì có nghĩa cho hệ thống của bạn).
Ví dụ 2
- Bạn đang sử dụng cấu trúc C có
char *
thành viên.
- Hệ thống của bạn không sử dụng phân bổ heap và bạn đang sử dụng kiểm tra MISRA.
- Giao diện của bạn chấp nhận cấu trúc này như một con trỏ và kiểm tra để đảm bảo rằng cấu trúc đó không trỏ đến
NULL
- Giá trị mặc định và an toàn của
char *
thành viên cho API của bạn có thể được biểu thị bằng một giá trị duy nhất làNULL
- Khi khởi tạo cấu trúc người dùng của bạn, bạn muốn cung cấp cho người dùng khả năng không khởi tạo
char *
thành viên một cách rõ ràng .
Trả lời: NULL
có thể phù hợp
Đặt vấn đề: Có một chút khả năng cấu trúc của bạn vượt qua NULL
kiểm tra nhưng chưa được khởi tạo. Tuy nhiên, API của bạn có thể không thể giải thích được điều này trừ khi bạn có một số loại tổng kiểm tra về giá trị cấu trúc và / hoặc kiểm tra phạm vi địa chỉ của cấu trúc. MISRA-C linters có thể giúp người dùng API của bạn bằng cách gắn cờ sử dụng các cấu trúc trước khi khởi tạo. Tuy nhiên, đối với char *
thành viên, nếu con trỏ tới struct trỏ đến cấu trúc được khởi tạo, NULL
là giá trị mặc định của thành viên không xác định trong trình khởi tạo cấu trúc. Do đó, NULL
có thể phục vụ như một giá trị mặc định, an toàn cho char *
thành viên struct trong ứng dụng của bạn.
Nếu trên giao diện tuần tự hóa, tôi sẽ tự hỏi mình những câu hỏi sau về việc có nên sử dụng null trên chuỗi hay không.
- Là
null
dấu hiệu của một lỗi phía khách hàng tiềm năng? Đối với JSON trong JavaScript, điều này có lẽ null
là không nhất thiết phải được sử dụng như một dấu hiệu của sự thất bại phân bổ. Trong JavaScript, nó được sử dụng như một dấu hiệu rõ ràng về sự vắng mặt của đối tượng khỏi một tham chiếu được đặt một cách có vấn đề. Tuy nhiên, có những trình phân tích cú pháp và trình tuần tự không phải là javascript để ánh xạ JSON null
thành null
kiểu gốc . Nếu đây là trường hợp, điều này đặt ra cuộc thảo luận về việc null
sử dụng bản địa có phù hợp với ngôn ngữ, trình phân tích cú pháp và trình kết nối cụ thể của bạn hay không .
- Sự vắng mặt rõ ràng của một giá trị tài sản có ảnh hưởng nhiều hơn một giá trị tài sản không? Đôi khi a
null
thực sự chỉ ra rằng bạn có một loại tin nhắn hoàn toàn mới. Người tiêu dùng của bạn có định dạng tuần tự hóa có thể sạch hơn khi chỉ định một loại thông báo hoàn toàn khác. Điều này đảm bảo rằng xác thực và logic ứng dụng của chúng có thể có sự tách biệt rõ ràng giữa hai sự khác biệt của các thông điệp mà giao diện web của bạn cung cấp.
Tư vấn chung
null
không thể là một giá trị trên một cạnh hoặc giao diện không hỗ trợ nó. Nếu bạn đang sử dụng thứ gì đó cực kỳ lỏng lẻo khi nhập các giá trị thuộc tính (ví dụ JSON), hãy thử đẩy một số dạng lược đồ hoặc xác thực trên phần mềm cạnh của người tiêu dùng (ví dụ: Lược đồ JSON ) nếu bạn có thể. Nếu đó là API ngôn ngữ lập trình, hãy xác thực tĩnh đầu vào của người dùng nếu có thể (thông qua nhập) hoặc to nhất có thể trong thời gian chạy (còn gọi là lập trình phòng thủ trên giao diện đối mặt với người tiêu dùng). Quan trọng là, tài liệu hoặc xác định cạnh để không có câu hỏi nào về:
- Loại giá trị nào mà một tài sản nhất định chấp nhận
- Phạm vi giá trị nào là hợp lệ cho một thuộc tính nhất định.
- Làm thế nào một loại tổng hợp nên được cấu trúc. Những thuộc tính nào phải / nên / có thể có trong một loại tổng hợp?
- Nếu đó là một số loại container, thì container có thể chứa bao nhiêu vật phẩm và các loại giá trị mà container chứa là gì?
- Thứ tự nào, nếu có, là các thuộc tính hoặc thể hiện của một loại container hoặc tổng hợp được trả về?
- Những tác dụng phụ nào có trong việc thiết lập các giá trị cụ thể và tác dụng phụ của việc đọc các giá trị đó là gì?