Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/141.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 如何从长指针中提取小尾端无符号短指针?_C++ - Fatal编程技术网

C++ 如何从长指针中提取小尾端无符号短指针?

C++ 如何从长指针中提取小尾端无符号短指针?,c++,C++,我有一个长指针值,它指向一个20字节的头结构,后跟一个更大的数组。Dec(57987104)=十六进制(0374D020)。所有值都存储在小端。交换时的1400为0014,十进制为20 这里的问题是如何获得第一个值,即2字节无符号短值。我有一个C++ DLL来为我转换这个。我正在运行Windows 10 GetCellData_API unsigned short __stdcall getUnsignedShort(unsigned long ptr) { unsigned lon

我有一个长指针值,它指向一个20字节的头结构,后跟一个更大的数组。Dec(57987104)=十六进制(0374D020)。所有值都存储在小端。交换时的1400为0014,十进制为20

这里的问题是如何获得第一个值,即2字节无符号短值。我有一个C++ DLL来为我转换这个。我正在运行Windows 10

GetCellData_API unsigned short __stdcall getUnsignedShort(unsigned long ptr) 
{
    unsigned long *p = &ptr;
    unsigned short ret = *p;
    return ret;
}
但是,当我使用
Debug.Print getUnsignedShort(57987104)
从VBA调用它时,当它应该是20时,我得到了30008

我可能需要做一个endian交换,但我不知道如何从

inline void endian_交换(无符号短x)
{
x=(x>>8)|

(x我想我倾向于用描述操作的通用模板函数来编写界面函数:

#include <utility>
#include <cstdint>

// Code for the general case
// you'll be amazed at the compiler's optimiser
template<class Integral>
auto extract_be(const std::uint8_t* buffer)
{
    using accumulator_type = std::make_unsigned_t<Integral>;

    auto acc = accumulator_type(0);
    auto count = sizeof(Integral);

    while(count--)
    {
        acc |= accumulator_type(*buffer++) << (8 * count);
    }

    return Integral(acc);
}



GetCellData_API unsigned short __stdcall getUnsignedShort(std::uintptr_t ptr) 
{
    return extract_be<std::uint16_t>(reinterpret_cast<const std::uint8_t*>(ptr));
}
#包括
#包括
//一般情况下的代码
//您会惊讶于编译器的优化程序
模板
自动提取(const std::uint8\u t*缓冲区)
{
使用累加器类型=std::make_unsigned_t;
自动acc=蓄能器类型(0);
自动计数=sizeof(整数);
而(计数--)
{

acc |=累加器类型(*buffer++)假设您用pulong pulong[6]指向表的第六个成员


无符号短psh*;
无符号字符puchar*
不易消化的焦炭[4];
零存储器(ptable,4);
puchar[3]=((char*)(&pulong[6]))[0];
puchar[2]=((char*)(&pulong[6]))[1];
puchar[1]=((char*)(&pulong[6]))[2];
puchar[0]=((char*)(&pulong[6]))[3];
psh=(无符号短*)puchar;
//第一个
psh[0];
//第二个
psh[1];

这是我误认为第二个无符号短值恰好为零时的想法。这是否容易转换以获得标题其余部分的长值?(仍在阅读/理解/测试)@D_Bester“所有值都以大端存储”。我想你是说“小端”对于你的新版本,我得到了-19957。仍然不好。@D_Bester你能发布一个MCVE并与我分享它来演示这个问题吗?@D_Bester因为它对我有用:这并没有回答我的问题。它甚至没有编译。我不知道如何将我的指针放入你的代码中,它也不会输出任何十进制值。所以这似乎不是r与我相关。如果这与
endian\u swap
相关,那么您错过了我的问题,应该删除此答案。我甚至不知道
endian\u swap
是否与我的问题相关。我想不是。不过,我感谢您抽出时间。
#include <utility>
#include <cstdint>

// Code for the general case
// you'll be amazed at the compiler's optimiser
template<class Integral>
auto extract_be(const std::uint8_t* buffer)
{
    using accumulator_type = std::make_unsigned_t<Integral>;

    auto acc = accumulator_type(0);
    auto count = sizeof(Integral);

    while(count--)
    {
        acc |= accumulator_type(*buffer++) << (8 * count);
    }

    return Integral(acc);
}



GetCellData_API unsigned short __stdcall getUnsignedShort(std::uintptr_t ptr) 
{
    return extract_be<std::uint16_t>(reinterpret_cast<const std::uint8_t*>(ptr));
}
template<class Integral>
auto extract_le(const std::uint8_t* buffer)
{
    using accumulator_type = std::make_unsigned_t<Integral>;

    auto acc = accumulator_type(0);
    constexpr auto size = sizeof(Integral);

    for(std::size_t count = 0 ; count < size ; ++count)
    {
        acc |= accumulator_type(*buffer++) << (8 * count);
    }

    return Integral(acc);
}


GetCellData_API unsigned short __stdcall getUnsignedShort(std::uintptr_t ptr) 
{
    return extract_le<std::uint16_t>(reinterpret_cast<const std::uint8_t*>(ptr));
}