มีประเภทข้อมูล 'ไบต์' ใน C ++ หรือไม่?


86

ถ้ามีอยู่มีไฟล์ส่วนหัวที่จะรวม?

รหัสนี้ให้ข้อผิดพลาดในการคอมไพล์:

#include <iostream>

using namespace std;

int main()
{
    byte b = 2;

    cout << b << endl;

    return 0;
}

15
เรียกว่าchar.
Avidan Borisov

12
@ Ben char คือจำเป็นต้องหนึ่งไบต์ แค่ไบต์ไม่จำเป็นต้องเป็น 8 บิต
Avidan Borisov

4
@ เบ็น: ดูเหมือนคุณจะไม่คุ้นเคยกับแพลตฟอร์มที่แปลกใหม่กว่านี้ที่มีอยู่ ไบต์ไม่ได้กำหนดให้เป็น 8 บิตอย่างแน่นอนโดยไม่คำนึงถึงข้อเท็จจริงที่ว่า 8 บิตไบต์นั้นเด่น CHAR_BITนั่นเป็นเหตุผลที่เรามี ฉันทำงานกับระบบฝังตัวมากกว่าหนึ่งระบบโดยที่ไบต์มีความยาวไม่เกิน 8 บิต ถ่านถูกกำหนดให้มีขนาด 1 ดังนั้นใช่ถ่านจึงเป็นไบต์เสมอ
Ed S.

11
@ เบ็น: มาตรฐาน C และ C ++ กำหนด "ไบต์" อย่างชัดเจนเป็นขนาดของ a charซึ่งมีค่าอย่างน้อย 8 บิต คำว่า "ไบต์" อาจกำหนดแตกต่างกันในบริบทอื่น ๆ แต่เมื่อพูดถึง C หรือ C ++ ควรยึดตามคำจำกัดความของมาตรฐาน
Keith Thompson

3
OP ฉันจะพิจารณาคำตอบที่คุณยอมรับอีกครั้ง จริงๆ. นอกจากนี้หากรับประกันว่าถ่านมีขนาด 1 เหตุใดจึงต้องเขียนบันทึกusing byte = unsigned charและทำด้วย (เช่นคำตอบของ rmp แนะนำ)
einpoklum

คำตอบ:


35

ไม่มีประเภทข้อมูลไบต์ใน C ++ อย่างไรก็ตามคุณสามารถรวมส่วนหัวบิตเซ็ตจากไลบรารีมาตรฐานและสร้าง typedef สำหรับไบต์:

typedef bitset<8> BYTE;

หมายเหตุ: เนื่องจาก WinDef.h กำหนด BYTE สำหรับรหัส windows คุณอาจต้องการใช้อย่างอื่นที่ไม่ใช่ BYTE หากคุณต้องการกำหนดเป้าหมาย Windows

แก้ไข: เพื่อตอบข้อเสนอแนะว่าคำตอบนั้นผิด คำตอบคือไม่ผิด คำถามคือ "มีประเภทข้อมูล" ไบต์ "ใน C ++ หรือไม่" คำตอบคือและคือ: "ไม่มีประเภทข้อมูลไบต์ใน C ++" ตามที่ตอบ

เกี่ยวกับทางเลือกที่เป็นไปได้ที่แนะนำซึ่งถูกถามว่าทำไมทางเลือกที่แนะนำจึงดีกว่า

ตามสำเนามาตรฐาน C ++ ของฉันในเวลา:

"ออบเจ็กต์ที่ประกาศเป็นอักขระ (ถ่าน) จะต้องมีขนาดใหญ่พอที่จะจัดเก็บสมาชิกใด ๆ ของชุดอักขระพื้นฐานของการนำไปใช้งาน": 3.9.1.1

ฉันอ่านแล้วเพื่อแนะนำว่าหากการใช้งานคอมไพเลอร์ต้องใช้ 16 บิตในการจัดเก็บสมาชิกของชุดอักขระพื้นฐานขนาดของอักขระจะเป็น 16 บิต คอมไพเลอร์ในปัจจุบันมักจะใช้ 8 บิตสำหรับ char เป็นสิ่งหนึ่ง แต่เท่าที่ฉันสามารถบอกได้ไม่มีการรับประกันอย่างแน่นอนว่ามันจะเป็น 8 บิต

ในทางกลับกัน "บิตเซ็ตเทมเพลตคลาส <N> อธิบายถึงออบเจ็กต์ที่สามารถจัดเก็บลำดับที่ประกอบด้วยจำนวนบิตคงที่, N" : 20.5.1. ในคำอื่น ๆ โดยระบุ 8 เป็นพารามิเตอร์เทมเพลตฉันลงท้ายด้วยอ็อบเจ็กต์ที่สามารถจัดเก็บลำดับที่ประกอบด้วย 8 บิต

ทางเลือกอื่นจะดีกว่าถ่านหรือไม่ในบริบทของโปรแกรมที่เขียนดังนั้นเท่าที่ฉันเข้าใจแม้ว่าฉันอาจจะผิดตามคอมไพเลอร์ของคุณและความต้องการของคุณในเวลานั้น ดังนั้นมันจึงขึ้นอยู่กับแต่ละคนที่เขียนโค้ดเท่าที่ฉันกังวลในการพิจารณาว่าทางเลือกที่แนะนำนั้นเหมาะสมกับความต้องการ / ความต้องการ / ความต้องการของพวกเขาหรือไม่


60
จะbitset<8>ดีกว่าunsigned charอย่างไร?
Keith Thompson

13
มันไม่ใช่. ใช้ถ่านที่ไม่ได้ลงนาม
YasserAsmi

2
คำตอบนั้นผิดและข้ออื่น ๆ ทั้งหมดผิดยกเว้น jwodder ซึ่งเป็นคำตอบเดียวที่ถูกต้อง ไบต์คือ BIT_CHAR บิตไม่ใช่ 8 บิต
Mark Galeck

14
คุณอาจต้องการอัปเดตคำตอบนี้เนื่องจากตอนนี้มีstd::byte
NathanOliver

1
@Persixty BIT_CHARโอ๊ะทำไมผมพูด มันเป็นเรื่องลึกลับ ความลึกลับของจักรวาล ..
Mark Galeck

88

ไม่ไม่มีประเภทที่เรียกว่า " byte" ใน C ++ สิ่งที่คุณต้องการแทนคือunsigned char(หรือถ้าคุณต้องการตรง 8 บิต, uint8_tจาก<cstdint>, ตั้งแต่ C ++ 11 ) โปรดทราบว่าcharไม่จำเป็นต้องเป็นทางเลือกอื่นที่ถูกต้องเนื่องจากหมายถึงsigned charคอมไพเลอร์บางตัวและตัวunsigned charอื่น ๆ


8
ไม่มาก char, signed charและunsigned charสามประเภทที่แตกต่างกัน charมีการแสดงเช่นเดียวกับหนึ่งในอีกสองรายการ
Keith Thompson

2
ถ้าunsigned charมีขนาดใหญ่กว่า 8 บิตuint8_tจะไม่ถูกกำหนด
Keith Thompson

1
ถ้าคุณอยู่ในวัตถุประสงค์ -c คุณอาจต้องรวมแทน<stdint.h> <cstdint>
orion elenzil

2
@orionelenzil คำถามเกี่ยวกับ C ++ ไม่ใช่วัตถุประสงค์ C.
Pharap

2
@pharap - หนึ่งการเขียน C หรือ C ++ ในบริบท Objective-C อาจพบว่าความคิดเห็นของฉันมีประโยชน์
orion elenzil

42

ใช่มีstd::byte(กำหนดไว้ใน<cstddef>)

C ++ 17แนะนำเลย


2
std::byteไม่สามารถคำนวณเลขคณิตได้ซึ่งอาจเป็นตัวทำลายข้อตกลง
Pharap

3
@Pharap มันขึ้นอยู่กับ - การไม่สามารถทำเลขคณิตโดยบังเอิญอาจถูกมองว่าเป็นข้อดีสำหรับบางกรณีการใช้งาน เนื่องจากstd::byteเป็นเพียงหนึ่งนอกจากนี้ยังสามารถเลือกเครื่องมือที่เหมาะสมสำหรับงาน (เช่นอย่างใดอย่างหนึ่งstd::byte, char, unsigned charหรือuint_8)
maxschlepzig


22

การใช้C++11มีเวอร์ชันที่ดีสำหรับประเภทไบต์ที่กำหนดด้วยตนเอง:

enum class byte : std::uint8_t {};

นั่นคือสิ่งที่GSLทำอย่างน้อย

เริ่มต้นด้วยC++17(เกือบ) เวอร์ชันนี้ถูกกำหนดไว้ในมาตรฐานว่าstd::byte(ขอบคุณ Neil Macintosh สำหรับทั้งสองอย่าง)


4
ทำไม enum ถึงดีกว่าในความคิดของคุณมากกว่าtypedef unsigned char byte;หรือtypedef std::uint8_t byte;?
einpoklum

2
@einpoklum เพิ่มความปลอดภัยในการพิมพ์ ตัวอย่างเช่นคุณได้รับข้อผิดพลาดในการคอมไพล์เมื่อคุณคูณค่าไบต์ดังกล่าวโดยไม่ได้ตั้งใจ แม้ว่าจะไม่ได้ช่วยให้มีรอยหยัก เมื่อคุณต้องการได้อย่างถูกต้องนามแฝงบางไบต์ที่คุณต้องการchar*, หรือunsigned char* std::byte*
maxschlepzig

1
ยกเว้นstd::byteไม่สามารถคำนวณเลขคณิตได้ซึ่งอาจเป็นตัวทำลายข้อตกลง
Pharap



1
namespace std
{
  // define std::byte
  enum class byte : unsigned char {};

};

หากเวอร์ชัน C ++ ของคุณไม่มี std :: byte จะกำหนดประเภทไบต์ใน namespace std โดยปกติคุณไม่ต้องการเพิ่มสิ่งต่างๆใน std แต่ในกรณีนี้มันเป็นสิ่งมาตรฐานที่หายไป

std :: byte จาก STL ทำงานได้มากขึ้น

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.