Làm thế nào để chuyển int thành enum trong C ++?


222

Làm cách nào để tôi chuyển int thành enum trong C ++?

Ví dụ:

enum Test
{
    A, B
};

int a = 1;

Làm cách nào để chuyển đổi asang loại Test::A?


1
link Lưu ý rằng không quan trọng liệu int có khớp với một trong các hằng số của kiểu enum hay không; việc chuyển đổi loại luôn là bất hợp pháp.
Iwaz

3
Tôi tin rằng nếu bạn muốn truyền sang Test :: Giá trị của int asẽ phải là 0, bởi vì Test :: A có giá trị ngầm định là 0 và Test :: B có giá trị ngầm định là 1. Trừ khi thực tế là truyền cụ thể là Test :: A nằm ngoài mục đích ...
JohnRDOrazio

Câu trả lời:


243
int i = 1;
Test val = static_cast<Test>(i);

21
tự động val = static_cast <Kiểm tra> (i); // C ++ 11
Mitch

3
@Mitch tôi nhận được gì khi sử dụng autotrong trường hợp này? Có bất kỳ cải tiến hiệu suất?
Frederico Pantuzza

2
Không cải thiện hiệu suất. Trình biên dịch chỉ tự động loại trừ nếu bạn chỉ định bằng "tự động". Nếu bạn quyết định thay đổi tên enum của mình trong tương lai, bạn sẽ sửa đổi mã của mình ít hơn vì trình biên dịch sẽ tự động suy ra tên loại chính xác.
Aydin Özcan

74
Test e = static_cast<Test>(1);

10
MSDN: Toán tử static_cast có thể chuyển đổi rõ ràng một giá trị tích phân thành một kiểu liệt kê. Nếu giá trị của loại tích phân không nằm trong phạm vi của các giá trị liệt kê, thì giá trị liệt kê kết quả là không xác định.
Kirill Kobelev

1
@KirillKobelev nếu giá trị tích phân có thể được biểu thị bằng loại cơ bản của enum thì enum kết quả phải có giá trị đó. Mặt khác, giá trị enum được tạo ra sẽ là bất kỳ giá trị nào dẫn đến việc chuyển đổi biểu thức thành kiểu cơ bản của enum. Nếu VC ++ làm điều gì đó khác biệt thì tôi nghĩ đó là không phù hợp.
bames53

2
Trình biên dịch tuân thủ nên làm gì, nếu enum có các giá trị {1,3,5} và mã cố gắng thực hiện <static_cast> từ giá trị của 2. Điều đó sẽ khác với diễn viên C như thế nào?
Kirill Kobelev

6
@KirillKobelev Tôi không sử dụng static_cast vì nó làm bất cứ điều gì khác với dàn diễn viên kiểu C, tôi đang sử dụng static_cast vì các phôi C ++ được ưa thích hơn so với các phôi C.
bames53

4
@KirillKobelev " nếu enum có các giá trị {1,3,5} " Không. Loại liệt kê không thể chỉ giới hạn ở 3 giá trị có thể này: {1,3,5} là các liệt kê (được đặt tên là giá trị liệt kê), không phải là liệt kê . Nếu 1,3,5 là giá trị liệt kê có thể , thì cũng là 2.
tò mò

25

Ma cua ban

enum Test
{
    A, B
}

int a = 1;

Giải pháp

Test castEnum = static_cast<Test>(a);

45
Đó là một ý tưởng tốt để sử dụng dàn diễn viên hạn chế nhất bạn có thể, và tránh hoàn toàn các kiểu kiểu C, để cung cấp cho trình biên dịch đó là cơ hội tốt nhất để phát hiện lỗi. static_castsẽ là một diễn viên tốt hơn ở đây.
Mike Seymour

4
@Mike Seymour, vấn đề là dàn diễn viên tĩnh không có sự khác biệt so với diễn viên C trong trường hợp này. Làm thế nào và những gì sai lầm nó có thể phát hiện ???
Kirill Kobelev

7
@KirillKobelev: Vấn đề là dàn diễn viên kiểu C không rõ ràng. Nó có thể bằng một static_cast, nhưng nó cũng có thể là const_casthoặc thậm chí tệ hơn, reinterpret_casthoặc thậm chí là sự kết hợp của những thứ đó. Ngay cả khi bạn biết bây giờ nó sẽ xuống cấp, giả sử sau này bạn đổi asang loại khác, thì đó rất có thể là kiểu thay đổi mà không bao giờ bạn nhận được nhiều cảnh báo, bạn không muốn điều đó.
KillianDS

4
@KillianDS " giả sử bạn thay đổi một loại khác sau này " loại nào?
tò mò

2
Có, hoặc những người hoặc một diễn viên ngầm nếu có. Nó rõ ràng hơn nhiều với ý định của các diễn viên là gì.
KillianDS

8

Bỏ qua câu hỏi đóng, "làm thế nào để tôi chuyển đổi thành loại Test::A" thay vì cứng nhắc về yêu cầu phải có một diễn viên trong đó, và trả lời muộn vài năm chỉ là câu hỏi phổ biến mà không ai khác có thể đề cập đến thay thế , theo tiêu chuẩn C ++ 11:

5.2.9 Diễn viên tĩnh

... một biểu thức ecó thể được chuyển đổi rõ ràng thành một loại T bằng cách sử dụng một static_castbiểu mẫu static_cast<T>(e)nếu khai báo T t(e);được định dạng tốt, đối với một số biến tạm thời được phát minh t(8,5). Hiệu quả của việc chuyển đổi rõ ràng như vậy giống như thực hiện khai báo và khởi tạo và sau đó sử dụng biến tạm thời làm kết quả của chuyển đổi.

Do đó, trực tiếp sử dụng biểu mẫu t(e)cũng sẽ hoạt động và bạn có thể thích nó cho gọn gàng:

auto result = Test(a);

giải pháp này hoạt động trong trường hợp tùy chọn trình biên dịch bị chặn static_cast <> (kiểm tra ngữ nghĩa). Không phải nó có ý nghĩa với tôi, nhưng vẫn gọn gàng.
Ông Buisson

1

Test castEnum = static_cast<Test>(a-1);sẽ chuyển từ thành A. Nếu bạn không muốn cấu trúc 1, bạn có thể xác định lại enum:

enum Test
{
    A:1, B
};

Trong trường hợp này `Test castEnum = static_cast (a); ' có thể được sử dụng để truyền a đến A.

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.