Copying 0 as 000 in C++? [closed] - c

It's difficult to tell what is being asked here. This question is ambiguous, vague, incomplete, overly broad, or rhetorical and cannot be reasonably answered in its current form. For help clarifying this question so that it can be reopened, visit the help center.
Closed 9 years ago.
This question is ANSWERED. Nothing to do with formatters but instead my idiocy when it comes to copying to new buffers.
I'm hoping this is a one line answer. I have a snprintf() statement which is something like the following:
snprintf(buffer, sizeof(buffer), "%03d", 0U);
I'm expecting buffer to hold 000 but for some reason it only holds 00. Assume the buffer is plenty large enough to hold what I want. Am I being silly?
EDIT:
See below for complete code with context. I was trying to simplify it before as I didn't think all this context was necessary. The point still remains, using %04u gives me 000 in the first CSV row. %03u only gives me 00.
uint16_t CSVGenerator::write_csv_data(TestRecord* record)
{
// Define the templates.
const char *row_template = "%04u,%6.3E,%6.3E,%6.3E,%6.3E,%6.3E\n";
char csv_row_buffer[CSV_ROW_BUFFER_SIZE];
// Add the data.
uint16_t row_count = 0U;
for (uint16_t reading = 0U; reading < MEASURE_READING_COUNT; ++reading)
{
// Parse the row.
snprintf(csv_row_buffer, sizeof(csv_row_buffer), row_template,
// Test ID
MEASURE_PERIOD_SECS * reading,
// Impedances Z1-Z5.
record->measurements[reading][0U],
record->measurements[reading][1U],
record->measurements[reading][2U],
record->measurements[reading][3U],
record->measurements[reading][4U]);
// Add it to the main buffer, excluding the terminator.
strncpy((m_csv_data_buffer + (reading * CSV_ROW_BUFFER_SIZE) - 1U),
csv_row_buffer, (sizeof(csv_row_buffer) - 1U));
// Increment the row count.
++row_count;
} // for : each reading.
return row_count;
}

How do you check that it contains only "000"? If you are reading it from (m_csv_data_buffer + (reading * CSV_ROW_BUFFER_SIZE)) you are actually losing the first byte since you've copied it to (m_csv_data_buffer + (reading * CSV_ROW_BUFFER_SIZE) - 1U) in your code.

strncpy handles null terminators implicitly so I'm guessing where you're subtracting 1 from the target buffer address you're actually putting the first character of your new row into the last byte of the previous row.
You seem to be using a combination of fixed buffer sizes and variable string lengths. This is what is the likely cause of what you're seeing.

are you on a 16bit machine? maybe you declared buffer as a char* so sizeof(buffer) evaluates as 2 and snprintf copies only the first two bytes of the actual output "000" (plus the terminator character 0x00)
I suspect the problem resides on how you read back the content of your buffer, not the actual content, maybe the:
Some dummy code to keep buffer in scope while I check it..
is way more important than what you posted

Related

I am trying to display a float value on an lcd , for the same I have to first convert it to a string.But it just doesn't work [closed]

It's difficult to tell what is being asked here. This question is ambiguous, vague, incomplete, overly broad, or rhetorical and cannot be reasonably answered in its current form. For help clarifying this question so that it can be reopened, visit the help center.
Closed 9 years ago.
weather.outdooe_temp is a float value which is being updated every time I press a button. set_temp is a float to ascii function. If I use that the thing works, but not if I use the code below.
char Thermo_Buff66[4];
static void SetBox(ScreenObj_t const *pS, EVENT_MSG const *pMsg)
{
//set_temp(weather.outdoor_temp,&a);//it works if i use this function.
sprintf(Thermo_Buff66,"%2.1f",weather.outdoor_temp);
(void)sprintf(Thermo_Buff,"%s\xc2\xb0""",Thermo_Buff66);
(void)DataBoxHandler(pS, &msg, "Set Temp", (uint8_t *)Thermo_Buff);
//currently displaying any # value....!!ing!!
}
char Thermo_Buff66[4];
sprintf(Thermo_Buff66,"%2.1f",weather.outdoor_temp);
The buffer you have allocated (Thermo_Buff66) is too short for a floating number representing outdoor temperature (often 2 digits) plus a . plus a digit after. Indeed, it doesn't have space for the terminating '\0' character. So immediate correction would be to set the size to 5. Still, in case of armageddon (or simply being in a non-SI country ... cough ... US), the temperature could even get to above 100, in which case again you overflow your buffer. Do yourself a favor and use snprintf.
Regardless, you sprintf into a buffer, then using %s you sprintf it into something else, which there is no point to. You can do it all directly in one, removing Thermo_Buff66 altogether:
(void)sprintf(Thermo_Buff, "%.1f\xc2\xb0", weather.outdoor_temp);
(void)DataBoxHandler(pS, &msg, "Set Temp", (uint8_t *)Thermo_Buff);
Side note: the . and the precision digit already take up 2 characters. Setting minimum width to 2 is therefore reduntant. Perhaps you thought the 2 in %2.1 is the number of digits before the .? Well it's not. It's the minimum overall width.

Problems with arrays in C [closed]

It's difficult to tell what is being asked here. This question is ambiguous, vague, incomplete, overly broad, or rhetorical and cannot be reasonably answered in its current form. For help clarifying this question so that it can be reopened, visit the help center.
Closed 10 years ago.
Given a shifted array (for example):
[17 34 190 1 4]
which shifted from (we don't know original)
[1 4 17 34 190]
What would be a good function to find the position of that number?
For example if I pass 1, it would return 3th position.
linear search for answer would always work, but I believe you can get there in O(log) time.
Some sort of binary search for the shift point via checking if the value of the shift sorted array goes against what it is supposed it. Like creating a trie. Keep forming the sorted tree until you find the "illegal" node (man this is glossing over a lot of details - I know). That tells you where the inflection point is and you now treat the array as 2 sorted vectors. Quickly check to see if the value to find is larger than the max entry of each so we know which vector to search. BSearch the sorted vector for your value and return its index.
The hard part is finding the inflection point. :)
You would have to scan the array.
size_t pos_in_arr(int *arr, size_t arr_size, int match)
{
size_t i;
for (i = 0; i < arr_size; i++)
if (arr[i] == match)
break;
return i;
}
This function would return the position as asked, or one more than the maximum position in case the element is not found.
The solution is what you ask, but it is probably not what you need, because it does not use in any way the fact that the array has been shifted. I suspect the original problem to be more complex.
For example if you knew that in the original array one element was fifth and now is seventh, and the element you are looking for was twenty-third, you could answer "twenty-fifth" without actually scanning the array up to the twenty-fifth position, which could be the point of the whole exercise. But to build such a solution, one would need to know more about the problem.

How to get the distinct count of a column using C [closed]

It's difficult to tell what is being asked here. This question is ambiguous, vague, incomplete, overly broad, or rhetorical and cannot be reasonably answered in its current form. For help clarifying this question so that it can be reopened, visit the help center.
Closed 10 years ago.
I would like to get the distinct count of the column of a large data file using C.How can I do it.Please kindly advise me.Thanks.My sample data file is as below.
For 2nd attribute the distinct count is 6.
399547,v4149,p3178,1990,2065,fraud
399940,v5852,p3194,8278,2180,fraud
399983,v3476,p3199,766,1125,fraud
400206,v3467,p3216,494,311000,fraud
400345,v4497,p3219,1211,432100,fraud
400471,v3473,p3225,41392,3710,fraud
400498,v3476,p3225,102,23820,fraud
401325,v4497,p3297,1322,1110,fraud
Make a search tree for every column. Let's say you have 10 rows in a file with 2 distinct values for the nth column viz. 3456 and 3457. Your search tree for nth column will look like:
You'll end up with 6 Search trees. Once you have read the entire file, traverse all possible paths in each search tree and that will give you the number of distinct values.
Read and split every line.
Put the second attributes into an array.
qsort the array
You have now an array with equal strings adjacent to each other. You can loop over the array and count different entries.
If your entries are all 5 characters long, otherwise you must malloc() memory for each attribute.
char (*array)[6];
int i;
int n; /* number of lines read */
int distinct = 1;
/* read the data file and put it into array */
/* qsort() array */
for (i = 1; i < n; ++i) {
if (strcmp(array[i], array[i - 1]) != 0)
++distinct;
}
printf("There are %d distinct rows\n", distinct);
You can use std::map<std::string,int> - it will hold key-value pairs, where key is vNNNN, and value is number of repetitions.
First loop will scan input file and populate this map, then number of keys in map will be distinct count.
EDIT: If you cannot use C++ and do require C, you will have to find some hashmap library for C, like sparsehash.
If amount of data is really, really big, it is possible that it will not fit in memory. In this case, I would recommend to use SQLite temporary database to parse, store and index your data and then use standard SELECT DISTINCT on it.

Write to a file in binary in C isn't working [closed]

It's difficult to tell what is being asked here. This question is ambiguous, vague, incomplete, overly broad, or rhetorical and cannot be reasonably answered in its current form. For help clarifying this question so that it can be reopened, visit the help center.
Closed 10 years ago.
I have an array of floats that I want to output to a file in binary. My relevant code is as follows:
FILE *binFile;
binFile = fopen(fileName, "wb");
if (binFile)
{
fwrite(completeList, sizeof(float), size, binFile);
}
Now, completeList is a pointer to an array of floats I was talking about, and size is another parameter I'm passing it indicating how many elements there are.
When this is outputted to a binary file, opening that file shows a bunch of random ASCII characters. I know this is what I should expect, but when I put it through a hex editor it shows random crap.
What am I doing wrong?
EDIT:
My parsing code:
FILE *bofFile = fopen(file, "rb");
if(bofFile)
{
float *tempArray;
fseek(bofFile, 0, SEEK_END);
unsigned long int size = ftell(bofFile) / sizeof(float);
tempArray = (float *)malloc(size);
fread(tempArray, sizeof(float), size, bofFile);
std::cout << tempArray[0];
}
Don't know if this is related, but you have a fairly serious problem here:
tempArray = malloc(size);
You should change that to prevent buffer overrun:
tempArray = malloc(size * sizeof(float));
Oh, and you also forgot to seek back to the start of the file before reading (that would be why it's "giving you nothing"):
fseek(bofFile, 0, SEEK_SET);
How is your input file formatted? Your code assumes that it too will look 'random' when viewed in a text editor. Have you tried displaying the entire array, to ensure you are reading the data from the input file correctly? Also, you have a malloc() problem that someone else pointed out.
The binary representation of the IEEE floating point format is not intuitive, and it will look like random data.

Array of a very long list of ints [closed]

It's difficult to tell what is being asked here. This question is ambiguous, vague, incomplete, overly broad, or rhetorical and cannot be reasonably answered in its current form. For help clarifying this question so that it can be reopened, visit the help center.
Closed 11 years ago.
I'm trying to solve the 8th problem of the project Euler and I'm stuck because I can't manage to create a very long array of char.
There must be a stupid semantic issue, but I'm unable to find it.
char cifre[] = "very long list of numbers here";
Such example works with gcc:
#include <stdio.h>
int main (void)
{
char *x =
"73167176531330624919225119674426574742355349194934\
96983520312774506326239578318016984801869478851843\
85861560789112949495459501737958331952853208805511\
12540698747158523863050715693290963295227443043557\
66896648950445244523161731856403098711121722383113\
62229893423380308135336276614282806444486645238749\
30358907296290491560440772390713810515859307960866\
70172427121883998797908792274921901699720888093776\
65727333001053367881220235421809751254540594752243\
52584907711670556013604839586446706324415722155397\
53697817977846174064955149290862569321978468622482\
83972241375657056057490261407972968652414535100474\
82166370484403199890008895243450658541227588666881\
16427171479924442928230863465674813919123162824586\
17866458359124566529476545682848912883142607690042\
24219022671055626321111109370544217506941658960408\
07198403850962455444362981230987879927244284909188\
84580156166097919133875499200524063689912560717606\
05886116467109405077541002256983155200055935729725\
71636269561882670428252483600823257530420752963450"
;
printf ("%s",x);
}
It prints your long number on screen without any problem. Symbol \ in string tells compiler that string literal is continued on next line. You are free to modify this example as you want. But please note that modifying content of string pointed by x isn't good idea.
Does adding a \ after each line of that 1000 digit number help?
It allows you to enter longer literals that span multiple lines.
Alternatively, surround each line of that long string in ", it will do the same thing.
As others have pointed out, you should probably allocate it dynamically. However, your question is somewhat vague as you didn't indicate where you are running into trouble or what your idea of "very long" is.
But here's some code to get you started:
#define ARRAY_SIZE 10240
char* pArray = (char*)malloc(ARRAY_SIZE);
memset(pArray, 0, ARRAY_SIZE);
free(pArray);

Resources