简体   繁体   English

如何在C中的char数组中存储2位整数值和浮点值

[英]How to store 2 digit integer value and float values in char array in C

Following is my C code to print values of char but I am getting unexpected results. 以下是我的C代码以打印char的值,但是得到了意外的结果。 The code is 该代码是

#include<stdio.h>

main()
{

  char sendBuffer[1000];
  float count;
  int i;
  for(count=1.5;count<=2.5;)
  {
   for(i=0;i<=15;)
   {
     sendBuffer[0]=count+48;
     sendBuffer[1]='a';
     sendBuffer[2]='b';
     sendBuffer[3]='c';
     sendBuffer[4]=i+48;
     sendBuffer[5]='\0';
     printf("%s\n",sendBuffer);
     i=i+5;
    }
   count=count+0.5;
  }
}

The results I am getting are: 我得到的结果是:

1abc0
1abc5
1abc:
1abc?
2abc0
2abc5
2abc:
2abc?
2abc0
2abc5
2abc:
2abc?

whereas, I was expecting something like 而我期待的是

1.5abc0
1.5abc5
1.5abc10
1.5abc15 

and so on. 等等。 Can anybody tell me how to store integer and float values in char array in C? 有人可以告诉我如何在C的char数组中存储整数和浮点值吗?

I see the answers you're getting answer the problem, but don't give an explanation, and from the looks of it, you could use a good explanation, so here's what's happening: 我看到您得到的答案已经回答了问题,但没有给出解释,从表面上看,您可以使用很好的解释,所以这是发生了什么:

Types in C C类型

You need to understand that different types ( int , char , float , double ) take up different sizes in memory. 您需要了解不同类型( intcharfloatdouble )在内存中占用不同的大小。 In C, a char is always considered to take up a single byte, and is in the range of -127 to 128. ( unsigned char goes from 0 to 255.) int s take up 4 bytes, and their range is from -2M to 2M - 1. float and double take 4 and 8 bytes respectively, and have a huge range, but limited precision. 在C语言中,始终将char视为一个字节,并且其范围为-127至128。( unsigned char的范围为0至255。) int s占用4个字节,范围为-2M到2M-1. floatdouble占用4和8个字节,并且范围很大,但精度有限。 (For more information, just search for "c type ranges", and you'll find lots of information, including these links on Stack Overflow, which also give you good explanations: Definition of range of a data type , Guarantateed minimum size/range of C data types ). (有关更多信息,只需搜索“ c类型范围”,您会发现很多信息,包括Stack Overflow上的这些链接,这些信息也为您提供了很好的解释: 数据类型范围的定义 ,保证的最小大小/范围C数据类型 )。

Also, you know enough ascii to know to add 48 to a digit to get the char version, but make sure you have an ascii table nearby. 另外,您知道足够的ascii知道要在数字上加上48以获取char版本,但是请确保附近有一个ascii表。 Conveniently, you can find one at http://www.asciitable.com . 方便地,您可以在http://www.asciitable.com上找到一个。

You also have to understand that the compiler will do its best to convert from one to another, though in some cases, such as casting a float to an int , if you don't do it explicitly, your compiler should at least issue a warning. 您还必须了解,编译器会尽最大努力将其转换为另一种,尽管在某些情况下,例如将float转换为int ,如果您未明确进行转换,则编译器至少应发出警告。

Strings don't exist as a type in C. Instead, you print into an array. 字符串在C中不作为类型存在。而是打印到数组中。 Other answers tell you how to do that. 其他答案告诉您如何执行此操作。 What their code is doing is printing the values you want into a character array, which is all you need. 他们的代码正在做的就是将所需的值打印到字符数组中,这就是您所需要的。

What your code is doing 您的代码在做什么

Now, let's see what your current code is doing: 现在,让我们看看您当前的代码在做什么:

First of all, a quick sidebar: when you're doing a for loop, it's best to put the increment in the loop itself, so: 首先,快速介绍一下:在执行for循环时,最好将增量放在循环本身中,因此:

for(count=1.5;count<=2.5;count=count+0.5)
{
  for(i=0;i<=15;i=i+5)

would be more standardized. 会更加标准化。

Now, your first line is sendBuffer[0]=count+48; 现在,您的第一行是sendBuffer[0]=count+48; . Here's what happens: 这是发生了什么:

  1. You're taking count, which starts at 1.5, and adding 48, so the first number is 49.5. 您正在计算,从1.5开始,再加上48,因此第一个数字是49.5。
  2. The compiler will automatically change a float to an int , though it should give you a warning about it. 编译器会自动将float更改为int ,尽管它会警告您。 It does so by truncating the value, changing 49.5 to 45. 它通过截断该值(将49.5更改为45)来实现。
  3. It then changes (int)49 to (char)49 which is the same value, but takes up one byte instead of 4. Ascii 49 is '1', so this happens to be the number you wanted. 然后它将(int)49更改为(char)49 ,这是相同的值,但占用一个字节而不是4。Ascii 49为'1',因此这恰好是您想要的数字。
  4. The compiler does not do anything with the rest of the float. 编译器与浮子的休息做任何事情。 It never sets sendBuffer[1] or [2] for this value. 它永远不会为此值设置sendBuffer [1]或[2]。

Your next 3 lines hard code the second, third and fourth characters of the string to abc . 接下来的3 abc字符串的第二个,第三个和第四个字符硬编码为abc Even if your first line had set the full float value into sendBuffer , this would overwrite it. 即使您的第一行将完整的float值设置为sendBuffer ,也会覆盖它。

Your final line takes i, which will be 0, 5, 10 and 15, and adds it to 48. This is just like the first step, without the truncation from float . 您的最后一行将i取为0、5、10和15,并将其加到48。这就像第一步一样,没有float截断。 So first it looks up ascii 48, which is '0', then ascii 53, which is '5'. 因此,首先查找ascii 48(即“ 0”),然后查找ascii 53(即“ 5”)。 When i is 10, it now takes the int 58 and converts it to a character (again, changing it from 4 bytes to 1 byte). i为10时,它现在使用int 58并将其转换为字符(再次将其从4字节更改为1字节)。 Printing ascii 58 results in ':', and printing ascii 63 results in '?'. 打印ascii 58结果为“:”,打印ascii 63结果为“?”。 And that's how your output ended up the way it did. 这就是输出结果的方式。

Possible solutions 可能的解决方案

Finally, a few words on the solution you were given: 最后,对解决方案说了几句话:

Since all you're doing is outputting the result, you don't need sendBuffer nor snprintf . 由于您要做的只是输出结果,因此不需要sendBuffersnprintf Simply using 只需使用

printf("%.1fabc%d\n", count, i);

would have sufficed. 就足够了。

It's instructive to think about what the printf family of functions does, though. 不过,考虑一下printf系列函数的功能很有启发性。 Though it's less efficient, let's use a few snprintf s to see what it's doing: 尽管效率较低,但让我们使用一些snprintf来查看其作用:

int index = 0;
index = snprintf(&sendbuf[index], sizeof(sendbuf) - index, "%.1f", count);
index += snprintf(&sendbuf[index], sizeof(sendbuf) - index, "abc");
index += snprintf(&sendbuf[index], sizeof(sendbuf) - index, "%d", i);
sendbuf[index++] = '\n';
sendbuf[index] = '\0';

What this does is what *printf does when you pass it multiple arguments: keep track of how much you've written and use that to tell where you're writing the next parts. *printf在传递多个参数时会执行以下操作:跟踪已编写的内容并使用它来告诉您接下来编写的位置。

If you don't know it, the a += b syntax is shorthand for a = a + b . 如果您不知道,则a += b语法是a = a + b简写。 a++ means "give me the value of a, then increment it." a++意思是“给我a的值,然后递增它”。

So the second line of my code will print out the float value into sendbuf, starting at the 0 position. 因此,我代码的第二行将从0位置开始将float值打印到sendbuf中。 *printf always returns the number of characters printed, so in this example, it will always print 3 characters, and I set index to 3. *printf始终返回打印的字符数,因此在此示例中,它将始终打印3个字符,并将index设置为3。

The next line writes the string abc into sendbuf, starting at position 3, and the line after that prints the value of i into position 6. Finally, I add the \\n for the new line, and the last line is the null terminator. 下一行将字符串abc写入sendbuf,从位置3开始,其后一行将i的值打印到位置6。最后,我在新行中添加\\ n,最后一行是空终止符。 I don't put index++ because I don't care about index any more, so don't need to bother incrementing it. 我不放置index++因为我不再关心索引,因此不必费心增加索引。 I put \\0 (as did you above) instead of 0, simply because \\0 reminds the programmer that we're dealing with a char array, not an integer array. 我把\\0 (如上所述)代替了0,仅仅是因为\\0提醒程序员我们正在处理char数组,而不是整数数组。

Again, all these lines aren't necessary, but since some of the issue seemed to be understanding what printf does, I thought it would be helpful. 同样,所有这些行都是不必要的,但是由于某些问题似乎是在理解printf功能,因此我认为这会有所帮助。

这可以工作:

snprintf(sendbuf, sizeof(sendbuf), "%.1fabc%d", count, i);

Add a byte to the output array. 向输出数组添加一个字节。 The first element needs 3 characters (bytes) not one. 第一个元素需要3个字符(字节)而不是一个。

sprintf(sendBuffer,"%0.1f",count);
sendBuffer[3] = 'a';
....

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM