C++ 相当于 Java ByteBuffer?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1466756/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-12 12:36:28  来源:igfitidea点击:

C++ equivalent of Java ByteBuffer?

javac++bytebuffer

提问by

I'm looking for a C++ "equivalent" of Java ByteBuffer.

我正在寻找 Java ByteBuffer 的 C++“等价物”。

I'm probably missing the obvious or just need an isolated usage example to clarify. I've looked through the iostream family & it looks like it may provide a basis. Specifically, I want to be able to:

我可能遗漏了明显的或只需要一个孤立的使用示例来澄清。我已经浏览了 iostream 系列,看起来它可以提供一个基础。具体来说,我希望能够:

  • build a buffer from a byte array/point and get primitives from the buffer, e.g. getByte, getInt
  • build a buffer using primitives e.g. putByte, putInt and then get the byte array/pointer.
  • 从字节数组/点构建缓冲区并从缓冲区获取原语,例如 getByte、getInt
  • 使用原语(例如 putByte、putInt)构建缓冲区,然后获取字节数组/指针。

采纳答案by AraK

You have stringbuf, filebufor you could use vector<char>.

你有stringbuffilebuf或者你可以使用vector<char>.



This is a simple example using stringbuf:

这是一个简单的例子,使用stringbuf

std::stringbuf buf;
char data[] = {0, 1, 2, 3, 4, 5};
char tempbuf[sizeof data];

buf.sputn(data, sizeof data); // put data
buf.sgetn(tempbuf, sizeof data); // get data


Thanks @Pete Kirkham for the idea of generic functions.

感谢@Pete Kirkham 提出泛型函数的想法。

#include <sstream>

template <class Type>
std::stringbuf& put(std::stringbuf& buf, const Type& var)
{
    buf.sputn(reinterpret_cast<const char*>(&var), sizeof var);

    return buf;
}

template <class Type>
std::stringbuf& get(std::stringbuf& buf, Type& var)
{
    buf.sgetn(reinterpret_cast<char*>(&var), sizeof(var));

    return buf;
}

int main()
{
    std::stringbuf mybuf;
    char byte = 0;
    int var;

    put(mybuf, byte++);
    put(mybuf, byte++);
    put(mybuf, byte++);
    put(mybuf, byte++);

    get(mybuf, var);
}

回答by Kirill V. Lyadvinsky

std::vector<char> bytes;

bytes.push_back( some_val ); // put

char x = bytes[N];           // get

const char* ptr = &bytes[0]; // pointer to array

回答by bua

for std::vector more efficient is method

对于 std::vector 更有效的是方法

push_back(T) 

You can find more here:

您可以在此处找到更多信息:

http://www.cppreference.com/wiki/stl/vector/start

http://www.cppreference.com/wiki/stl/vector/start

and general about cpp stl libs

和关于 cpp stl 库的一般信息

http://www.cppreference.com/wiki/stl/start

http://www.cppreference.com/wiki/stl/start

There are many containers, depends what do You need it for,

有很多容器,取决于你需要它做什么,

  • speed aggregation (fast writing capabilities) or
  • fast read
  • 速度聚合(快速写入功能)或
  • 快速阅读

take a look at std::list, std::vector.

看看 std::list 和 std::vector。

回答by Pete Kirkham

stringstreamprovides basic unformatted getand writeoperations to write blocks of chars. To specialise on Teither subclass or wrap it, or provide free standing template functions to use the get/write appropriately sized memory.

stringstream提供基本的未格式化getwrite写入字符块的操作。专注于T子类或包装它,或提供独立的模板函数来使用获取/写入适当大小的内存。

template <typename T>
std::stringstream& put ( std::stringstream& str, const T& value )
{
    union coercion { T value; char   data[ sizeof ( T ) ]; };

    coercion    c;

    c.value = value;

    str.write ( c.data, sizeof ( T ) );

    return str;
}

template <typename T>
std::stringstream& get ( std::stringstream& str, T& value )
{
    union coercion { T value; char   data[ sizeof ( T ) ]; };

    coercion    c;

    c.value = value;

    str.read ( c.data, sizeof ( T ) );

    value = c.value;

    return str;
}

You could write such templates for whatever other stream or vector you want - in the vector's case, it would need to use insert rather than write.

您可以为您想要的任何其他流或向量编写此类模板 - 在向量的情况下,它需要使用插入而不是写入。

回答by Pete Kirkham

Thanks for all the input, it has lead to this pretty simple solution:

感谢所有输入,它导致了这个非常简单的解决方案:


class ByteBuffer : std::stringbuf
{
public:
    template 
    size_t get( T &out)
    {
        union coercion { T value; char data[ sizeof ( T ) ]; };

        coercion c;

        size_t s= xsgetn( c.data, sizeof(T));

        out= c.value;

        return s;
    }

    template 
    size_t put( T &in)
    {   
        union coercion { T value; char data[ sizeof ( T ) ]; };

        coercion c;

        c.value= in;

        return xsputn( c.data, sizeof(T));
    }

    size_t get( uint8_t *out, size_t count)
    {
        return xsgetn((char *)out, count);
    }

    size_t put( uint8_t *out, size_t count)
    {
        return xsputn((char *)out, count);
    }
};

To use eg:

使用例如:


void ByteBufferTest( void)
{
    ByteBuffer bb;

    float f= 4;
    uint8_t u8= 1;
    uint16_t u16= 2;
    uint32_t u32= 4;
    uint64_t u64= 8;

    bb.put(f);
    bb.put(u8);
    bb.put(u16);
    bb.put(u32);
    bb.put(u64);

    uint8_t array[19];

    bb.get( array, 19);

    // or

    bb.get(f);
    bb.get(u8);
    bb.get(u16);
    bb.get(u32);
    bb.get(u64);
}

回答by Ramsey

I wrote this awhile back to do exactly what you're asking for. Give it a shot:

我写这篇文章是为了完全按照你的要求去做。试一试:

https://github.com/RamseyK/ByteBufferCpp

https://github.com/RamseyK/ByteBufferCpp