C++;从int*到void*再到char*的静态转换-你能帮我理解这段代码吗? 我是C++初学者,我对理解一些代码有问题。
我要做一个练习,编写返回C++;从int*到void*再到char*的静态转换-你能帮我理解这段代码吗? 我是C++初学者,我对理解一些代码有问题。,c++,static-cast,C++,Static Cast,我要做一个练习,编写返回int大小的函数,并且不使用sizeof()和重新解释cast。有人给了我解决方案,但我不明白它是如何工作的。你能帮我理解一下吗?代码如下: int intSize() { int intArray[10]; int * intPtr1; int * intPtr2; intPtr1 = &intArray[1]; intPtr2 = &intArray[2]; //Why cast int pointer to void po
int
大小的函数,并且不使用sizeof()
和重新解释cast
。有人给了我解决方案,但我不明白它是如何工作的。你能帮我理解一下吗?代码如下:
int intSize() {
int intArray[10];
int * intPtr1;
int * intPtr2;
intPtr1 = &intArray[1];
intPtr2 = &intArray[2];
//Why cast int pointer to void pointer?
void* voidPtr1 = static_cast<void*>(intPtr1);
//why cast void pointer to char pointer?
char* charPtr1 = static_cast<char*>(voidPtr1);
void* voidPtr2 = static_cast<void*>(intPtr2);
char* charPtr2 = static_cast<char*>(voidPtr2);
//when I try to print 'charPtr1' there is nothing printed
//when try to print charPtr2 - charPtr1, there is correct value shown - 4, why?
return charPtr2 - charPtr1;
}
int intSize(){
int intArray[10];
int*intPtr1;
int*intPtr2;
intPtr1=&intArray[1];
intPtr2=&intArray[2];
//为什么将int指针强制转换为void指针?
void*voidPtr1=静态浇铸(intPtr1);
//为什么将void指针强制转换为char指针?
char*charPtr1=静态_铸造(voidPtr1);
void*voidPtr2=静态浇铸(intPtr2);
char*charPtr2=静态_铸造(voidPtr2);
//当我尝试打印“charPtr1”时,没有打印任何内容
//当尝试打印charPtr2-charPtr1时,显示了正确的值-4,为什么?
返回charPtr2-charPtr1;
}
总而言之,我不明白的是,为什么我们必须将
int*
更改为void*
,然后更改为char*
来执行此任务?为什么我们在减去charPtr2
和charPtr1
时会得到结果,但在尝试仅打印charPtr1
时却没有显示结果?这是重要的一点:
intPtr1 = &intArray[1];
intPtr2 = &intArray[2];
这将创建两个指向数组中相邻整数的指针。这两个指针之间的距离是您试图检索的整数的大小。然而,指针算法的工作方式是,如果你减去这两个,那么编译器将返回你整数的大小,它总是1
因此,接下来要做的是将这些字符重新转换为字符指针。每个字符(或事实上是)1个字节,因此这两个指针作为字符指针之间的差异将以字节为单位给出答案。这就是为什么你要使用字符指针和减法
至于via
void*
——这是为了避免使用重新解释cast
。不允许使用static\u cast
直接从int*
转换为char*
,但通过void*
将删除此限制,因为编译器不再知道它是以int*
开头的。您也可以只使用C样式转换,(char*)(intPtr1)
首先,不要在实际代码中这样做。你会摔断你的腿,看起来像个白痴,所有酷孩子都会嘲笑你
话虽如此,它的工作原理如下:
基本思想是int的大小等于int数组中两个元素之间的偏移量(以字节为单位)。数组中的整数是紧密压缩的,因此第二个整数的开头正好在第一个整数的结尾之后:
int* intPtr1 = &intArray[0];
int* intPtr2 = &intArray[1];
这里的问题是,当减去两个int指针时,不会得到以字节为单位的差值,而是以int为单位的差值。因此,intPtr2-intPtr1
是1
,因为它们相距1 int
<>但是我们是C++的,所以我们可以把指针投向任何东西!因此,我们不使用int指针,而是将值复制到char指针,char指针的大小为1字节(至少在大多数平台上是这样)
char*charPtr1=重新解释强制转换(intPtr1);
char*charPtr2=重新解释(intPtr2);
差异charPtr2-charPtr1
是以字节为单位的大小。指针仍然指向与以前相同的位置(即数组中第二个和第一个int的起始位置),但现在将以char
的大小计算差异,而不是以int
的大小计算差异
由于练习不允许重新解释施法,您将不得不使用另一个技巧。您不能直接从
int*
到char*
进行static\u转换。这是C++保护你不做傻事的方法。诀窍是先将其转换为void*
。您可以将static\u转换为void*
的任何指针类型,也可以从void*
转换为任何指针类型。请阅读:评论丰富
int intSize()
{
int intArray[2]; // Allocate two elements. We don't need any more than that.
/*intPtr1 and intPtr2 point to the addresses of the zeroth and first array elements*/
int* intPtr1 = &intArray[0]; // Arrays in C++ are zero based
int* intPtr2 = &intArray[1];
/*Note that intPtr2 - intPtr1 measures the distance in memory
between the array elements in units of int*/
/*What we want to do is measure that distance in units of char;
i.e. in bytes since once char is one byte*/
/*The trick is to cast from int* to char*. In c++ you need to
do this via void* if you are not allowed to use reinterpret_cast*/
void* voidPtr1 = static_cast<void*>(intPtr1);
char* charPtr1 = static_cast<char*>(voidPtr1);
void* voidPtr2 = static_cast<void*>(intPtr2);
char* charPtr2 = static_cast<char*>(voidPtr2);
/*The distance in memory will now be measure in units of char;
that's how pointer arithmetic works*/
/*Since the original array is a contiguous memory block, the
distance will be the size of each element, i.e. sizeof(int) */
return charPtr2 - charPtr1;
}
int intSize()
{
int intArray[2];//分配两个元素。我们不需要更多的元素。
/*intPtr1和intPtr2指向第0个和第一个数组元素的地址*/
INT*INTRT1=和INTARTRAY(0);// C++中的数组是零基的
int*intPtr2=&intArray[1];
/*注意,intPtr2-intPtr1测量内存中的距离
以int为单位的数组元素之间*/
/*我们要做的是以字符为单位测量距离;
i、 e.以字节为单位,因为once char是一个字节*/
*技巧是从int *到char *。在C++中,你需要
如果不允许使用reinterpret_cast,请通过void*执行此操作*/
void*voidPtr1=静态浇铸(intPtr1);
char*charPtr1=静态_铸造(voidPtr1);
void*voidPtr2=静态浇铸(intPtr2);
char*charPtr2=静态_铸造(voidPtr2);
/*内存中的距离现在将以字符为单位测量;
指针算法就是这样工作的*/
/*由于原始数组是连续内存块,因此
距离将是每个元素的大小,即sizeof(int)*/
返回charPtr2-charPtr1;
}
在C++中指针减法给出了元素之间的元素个数。
这个指针指向物体。换句话说,intPtr2-intPtr1
将返回这两个指针之间的int
数。
程序想知道字节数(char
),因此
将int*
转换为char*
。显然,作者没有
要使用重新解释强制转换
也可以。和static\u cast
will
不允许从int*
直接转换为char*
,因此
通过void*
(这是允许的)
说了这么多:从函数名和
指针实际上是如何初始化的,一个简单得多的方法
实施这项工作
int intSize()
{
int intArray[2]; // Allocate two elements. We don't need any more than that.
/*intPtr1 and intPtr2 point to the addresses of the zeroth and first array elements*/
int* intPtr1 = &intArray[0]; // Arrays in C++ are zero based
int* intPtr2 = &intArray[1];
/*Note that intPtr2 - intPtr1 measures the distance in memory
between the array elements in units of int*/
/*What we want to do is measure that distance in units of char;
i.e. in bytes since once char is one byte*/
/*The trick is to cast from int* to char*. In c++ you need to
do this via void* if you are not allowed to use reinterpret_cast*/
void* voidPtr1 = static_cast<void*>(intPtr1);
char* charPtr1 = static_cast<char*>(voidPtr1);
void* voidPtr2 = static_cast<void*>(intPtr2);
char* charPtr2 = static_cast<char*>(voidPtr2);
/*The distance in memory will now be measure in units of char;
that's how pointer arithmetic works*/
/*Since the original array is a contiguous memory block, the
distance will be the size of each element, i.e. sizeof(int) */
return charPtr2 - charPtr1;
}
int
intSize()
{
return sizeof( int );
}
#include <limits>
int intSize()
{
// digits returns non-sign bits, so add 1 and divide by 8 (bits in a byte)
return (std::numeric_limits<int>::digits+1)/8;
}