在c中使用整数数组的memset

时间:2021-08-30 16:09:00
char str[]="beautiful earth";
memset(str,'*',6);
printf("%s",str);

output:
******ful earth

1) Like above use of memset, can we initialize only few integer array index values to 1 as given below??

1)像上面使用的memset一样,我们只能初始化几个整数数组索引值为1,如下所示?

int arr[15];
memset(arr,1,6);

9 个解决方案

#1


32  

No, you cannot use memset() like this. The manpage says (emphasis mine):

不,你不能像这样使用memset()。该联机帮助页(强调我的):

The memset() function fills the first n bytes of the memory area pointed to by s with the constant byte c.

memset()函数用常量字节c填充s指向的存储区的前n个字节。

Since an int is usually 4 or 8 bytes, this won't cut it.

由于int通常是4或8个字节,因此不会删除它。


If you (incorrectly!!) try to do this:

如果你(错误!!)尝试这样做:

int arr[15];
memset(arr, 1, 6*sizeof(int));    //wrong!

then the first 6 ints in the array will actually be set to 0x01010101 = 16843009.

然后数组中的前6个实际上将设置为0x01010101 = 16843009。

The only time it's ever really acceptable to write over a "blob" of data with non-byte datatype(s), is memset(thing, 0, sizeof(thing)); to "zero-out" the whole struture/array. This works because NULL, 0x00000000, 0.0, are all completely zeros.

使用非字节数据类型写入“blob”数据的唯一时间是memset(thing,0,sizeof(thing));将整个结构/阵列“归零”。这是有效的,因为NULL,0x00000000,0.0都是完全零。


The solution is to use a for loop and set it yourself:

解决方案是使用for循环并自己设置:

int arr[15];
int i;

for (i=0; i<6; ++i)    // Set the first 6 elements in the array
    arr[i] = 1;        // to the value 1.

#2


12  

Short answer, NO.

简短的回答,没有。

Long answer, memset sets bytes and works for characters because they are single bytes, but integers are not.

长答案,memset设置字节并为字符工作,因为它们是单字节,但整数不是。

#3


3  

The third argument of memset is byte size. So you should set total byte size of arr[15]

memset的第三个参数是字节大小。所以你应该设置arr的总字节大小[15]

memset(arr, 1, sizeof(arr));

However probably, you should want to set value 1 to whole elements in arr. Then you've better to set in the loop.

但是,您可能希望将值1设置为arr中的整个元素。然后你最好设置循环。

for (i = 0; i < sizeof(arr)/sizeof(arr[0]); i++) {
    arr[i] = 1;
}

Because memset() set 1 in each bytes. So it's not your expected.

因为memset()在每个字节中设置为1。所以这不是你的期望。

#4


2  

On Linux, OSX and other UNIX like operating systems where wchar_t is 32 bits and you can use wmemset() instead of memset().

在Linux,OSX和其他UNIX操作系统上,其中wchar_t是32位,您可以使用wmemset()而不是memset()。

#include<wchar.h>
...
int arr[15];
wmemset( arr, 1, 6 );

Note that wchar_t on MS-Windows is 16 bits so this trick may not work.

请注意,MS-Windows上的wchar_t是16位,因此这个技巧可能无效。

#5


0  

Since nobody mentioned it...

既然没有人提到它......

Although you cannot initialize the integers with value 1 using memset, you can initialize them with value -1 and simply change your logic to work with negative values instead.

虽然您无法使用memset初始化值为1的整数,但您可以使用值-1初始化它们,只需更改逻辑以使用负值。

For example, to initialize the first 6 numbers of your array with -1, you would do

例如,要用-1初始化数组的前6个数字,就可以了

memset(arr,-1,6*(sizeof int));

Furthermore, if you only need to do this initialization once, you can actually declare the array to start with values 1 from compile time.

此外,如果您只需要执行一次初始化,您实际上可以将数组声明为从编译时开始的值为1。

int arr[15] = {1,1,1,1,1,1};

#6


0  

No, you can't [portably] use memset for that purpose, unless the desired target value is 0. memset treats the target memory region as an array of bytes, not an array of ints.

不,你不能[移植]为此目的使用memset,除非所需的目标值是0. memset将目标内存区域视为一个字节数组,而不是一个int数组。

A fairly popular hack for filling a memory region with a repetitive pattern is actually based on memcpy. It critically relies on the expectation that memcpy copies data in forward direction

用重复模式填充内存区域的相当流行的hack实际上是基于memcpy。它严重依赖于memcpy向前复制数据的期望

int arr[15];

arr[0] = 1;
memcpy(&arr[1], &arr[0], sizeof arr - sizeof *arr);

This is, of course, a pretty ugly hack, since the behavior of standard memcpy is undefined when the source and destination memory regions overlap. You can write your own version of memcpy though, making sure it copies data in forward direction, and use in the above fashion. But it is not really worth it. Just use a simple cycle to set the elements of your array to the desired value.

当然,这是一个相当丑陋的黑客,因为当源和目标内存区域重叠时,标准memcpy的行为是未定义的。您可以编写自己的memcpy版本,确保它向前复制数据,并以上述方式使用。但这不值得。只需使用一个简单的循环将数组的元素设置为所需的值。

#7


0  

Memset sets values for data types having 1 byte but integers have 4 bytes or more , so it won't work and you'll get garbage values. It's mostly used when you are working with char and string types.

Memset为具有1个字节的数据类型设置值,但是整数具有4个字节或更多,因此它将不起作用并且您将获得垃圾值。它主要用于处理char和string类型时。

#8


0  

I tried the following program and it appears that you can initialize your array using memset() with -1 and 0 only

我尝试了以下程序,看起来您可以使用memset()初始化您的数组,仅使用-1和0

#include<stdio.h>
#include<string.h>

void printArray(int arr[], int len)
{
        int i=0;
    for(i=0; i<len; i++)
    {
        printf("%d ", arr[i]);
    }
    puts("");
}

int main()
{
    int arrLen = 15;
    int totalNoOfElementsToBeInitialized = 6;

    int arr[arrLen];
    printArray(arr, arrLen);
    memset(arr, -1, totalNoOfElementsToBeInitialized*sizeof(arr[0]));
    printArray(arr, arrLen);
    memset(arr, 0, totalNoOfElementsToBeInitialized*sizeof(arr[0]));
    printArray(arr, arrLen);
    memset(arr, 1, totalNoOfElementsToBeInitialized*sizeof(arr[0]));
    printArray(arr, arrLen);
    memset(arr, 2, totalNoOfElementsToBeInitialized*sizeof(arr[0]));
    printArray(arr, arrLen);
    memset(arr, -2, totalNoOfElementsToBeInitialized*sizeof(arr[0]));
    printArray(arr, arrLen);
    return 0;
}

#9


-5  

memset((char *)&tab, 0, sizeof(tab));

#1


32  

No, you cannot use memset() like this. The manpage says (emphasis mine):

不,你不能像这样使用memset()。该联机帮助页(强调我的):

The memset() function fills the first n bytes of the memory area pointed to by s with the constant byte c.

memset()函数用常量字节c填充s指向的存储区的前n个字节。

Since an int is usually 4 or 8 bytes, this won't cut it.

由于int通常是4或8个字节,因此不会删除它。


If you (incorrectly!!) try to do this:

如果你(错误!!)尝试这样做:

int arr[15];
memset(arr, 1, 6*sizeof(int));    //wrong!

then the first 6 ints in the array will actually be set to 0x01010101 = 16843009.

然后数组中的前6个实际上将设置为0x01010101 = 16843009。

The only time it's ever really acceptable to write over a "blob" of data with non-byte datatype(s), is memset(thing, 0, sizeof(thing)); to "zero-out" the whole struture/array. This works because NULL, 0x00000000, 0.0, are all completely zeros.

使用非字节数据类型写入“blob”数据的唯一时间是memset(thing,0,sizeof(thing));将整个结构/阵列“归零”。这是有效的,因为NULL,0x00000000,0.0都是完全零。


The solution is to use a for loop and set it yourself:

解决方案是使用for循环并自己设置:

int arr[15];
int i;

for (i=0; i<6; ++i)    // Set the first 6 elements in the array
    arr[i] = 1;        // to the value 1.

#2


12  

Short answer, NO.

简短的回答,没有。

Long answer, memset sets bytes and works for characters because they are single bytes, but integers are not.

长答案,memset设置字节并为字符工作,因为它们是单字节,但整数不是。

#3


3  

The third argument of memset is byte size. So you should set total byte size of arr[15]

memset的第三个参数是字节大小。所以你应该设置arr的总字节大小[15]

memset(arr, 1, sizeof(arr));

However probably, you should want to set value 1 to whole elements in arr. Then you've better to set in the loop.

但是,您可能希望将值1设置为arr中的整个元素。然后你最好设置循环。

for (i = 0; i < sizeof(arr)/sizeof(arr[0]); i++) {
    arr[i] = 1;
}

Because memset() set 1 in each bytes. So it's not your expected.

因为memset()在每个字节中设置为1。所以这不是你的期望。

#4


2  

On Linux, OSX and other UNIX like operating systems where wchar_t is 32 bits and you can use wmemset() instead of memset().

在Linux,OSX和其他UNIX操作系统上,其中wchar_t是32位,您可以使用wmemset()而不是memset()。

#include<wchar.h>
...
int arr[15];
wmemset( arr, 1, 6 );

Note that wchar_t on MS-Windows is 16 bits so this trick may not work.

请注意,MS-Windows上的wchar_t是16位,因此这个技巧可能无效。

#5


0  

Since nobody mentioned it...

既然没有人提到它......

Although you cannot initialize the integers with value 1 using memset, you can initialize them with value -1 and simply change your logic to work with negative values instead.

虽然您无法使用memset初始化值为1的整数,但您可以使用值-1初始化它们,只需更改逻辑以使用负值。

For example, to initialize the first 6 numbers of your array with -1, you would do

例如,要用-1初始化数组的前6个数字,就可以了

memset(arr,-1,6*(sizeof int));

Furthermore, if you only need to do this initialization once, you can actually declare the array to start with values 1 from compile time.

此外,如果您只需要执行一次初始化,您实际上可以将数组声明为从编译时开始的值为1。

int arr[15] = {1,1,1,1,1,1};

#6


0  

No, you can't [portably] use memset for that purpose, unless the desired target value is 0. memset treats the target memory region as an array of bytes, not an array of ints.

不,你不能[移植]为此目的使用memset,除非所需的目标值是0. memset将目标内存区域视为一个字节数组,而不是一个int数组。

A fairly popular hack for filling a memory region with a repetitive pattern is actually based on memcpy. It critically relies on the expectation that memcpy copies data in forward direction

用重复模式填充内存区域的相当流行的hack实际上是基于memcpy。它严重依赖于memcpy向前复制数据的期望

int arr[15];

arr[0] = 1;
memcpy(&arr[1], &arr[0], sizeof arr - sizeof *arr);

This is, of course, a pretty ugly hack, since the behavior of standard memcpy is undefined when the source and destination memory regions overlap. You can write your own version of memcpy though, making sure it copies data in forward direction, and use in the above fashion. But it is not really worth it. Just use a simple cycle to set the elements of your array to the desired value.

当然,这是一个相当丑陋的黑客,因为当源和目标内存区域重叠时,标准memcpy的行为是未定义的。您可以编写自己的memcpy版本,确保它向前复制数据,并以上述方式使用。但这不值得。只需使用一个简单的循环将数组的元素设置为所需的值。

#7


0  

Memset sets values for data types having 1 byte but integers have 4 bytes or more , so it won't work and you'll get garbage values. It's mostly used when you are working with char and string types.

Memset为具有1个字节的数据类型设置值,但是整数具有4个字节或更多,因此它将不起作用并且您将获得垃圾值。它主要用于处理char和string类型时。

#8


0  

I tried the following program and it appears that you can initialize your array using memset() with -1 and 0 only

我尝试了以下程序,看起来您可以使用memset()初始化您的数组,仅使用-1和0

#include<stdio.h>
#include<string.h>

void printArray(int arr[], int len)
{
        int i=0;
    for(i=0; i<len; i++)
    {
        printf("%d ", arr[i]);
    }
    puts("");
}

int main()
{
    int arrLen = 15;
    int totalNoOfElementsToBeInitialized = 6;

    int arr[arrLen];
    printArray(arr, arrLen);
    memset(arr, -1, totalNoOfElementsToBeInitialized*sizeof(arr[0]));
    printArray(arr, arrLen);
    memset(arr, 0, totalNoOfElementsToBeInitialized*sizeof(arr[0]));
    printArray(arr, arrLen);
    memset(arr, 1, totalNoOfElementsToBeInitialized*sizeof(arr[0]));
    printArray(arr, arrLen);
    memset(arr, 2, totalNoOfElementsToBeInitialized*sizeof(arr[0]));
    printArray(arr, arrLen);
    memset(arr, -2, totalNoOfElementsToBeInitialized*sizeof(arr[0]));
    printArray(arr, arrLen);
    return 0;
}

#9


-5  

memset((char *)&tab, 0, sizeof(tab));