Use of '%06.3f' in a C program - c

#include<stdio.h>
main()
{
int Fahrenheit;
for (Fahrenheit = 0; Fahrenheit <= 300; Fahrenheit = Fahrenheit + 20)
printf("%3d %06.3f\n", Fahrenheit, (5.0/9.0)*(Fahrenheit-32));
}
Output of the source above:
0 -17.778
20 -6.667
40 04.444
60 15.556
80 26.667
100 37.778
120 48.889
140 60.000
160 71.111
180 82.222
200 93.333
220 104.444
240 115.556
260 126.667
280 137.778
300 148.889
Please explain to me the function of '06.3f' in the 'printf' function in the program above.

0 fill with 0 on the left
6 the string should be at least 6 characters long
.3 precision is 3 digits after the decimal point
f it accepts a float (or double) variable

Related

Reading into an array from a txt file

So, I'm trying to get my program to read into an array of structs from a text file, and it compiles okay, but doesnt appear to actually be reading in the values?.. and I have no idea why. This is the relevant part of the code:
typedef struct Planet
{
char Planet_Name[30];
double Fuel;
double Velocity;
double Height;
double Gravity;
int Maximum_Thrust;
double Difficulty;
}Planet;
//read the Planets from a file
FILE* inputFile = fopen("Planets.txt", "r");
if(inputFile == NULL)
{
perror("Error. File unavailable");
exit(1);
}
for(j=0; j<10; j++)
{
fscanf("%29s %lf %lf %lf %lf %d %lf", SolarSystem[j].Planet_Name,
SolarSystem[j].Fuel, SolarSystem[j].Velocity,
SolarSystem[j].Height, SolarSystem[j].Gravity,
SolarSystem[j].Maximum_Thrust, SolarSystem[j].Difficulty);
}
printf("Please select a planet by entering the corresponding number:
Mercury[0], Venus[1], Earth[2], Moon[3], Mars[4], Jupiter[5], Saturn[6],
Uranus[7], Neptune[8]\n");
scanf("%d",&PlanetNum);
printf("You have chosen %s", SolarSystem[PlanetNum].Planet_Name);
This is the txt file (Title: Planets.txt)
Mercury 120 50 500 12.1 30 2
Venus 120 50 500 29.1 30 6
Earth 120 50 500 32.2 30 7
Moon 120 15 50 5.3 30 2
Mars 120 50 500 12.2 30 4
Jupiter 120 50 500 81.3 30 10
Saturn 120 50 500 34.3 30 8
Uranus 120 50 500 28.5 30 5
Neptune 120 50 500 36.6 30 9
Pluto 120 50 500 2.03 30 1
Except when it runs that final printf, it doesn't actually print anything, nor does it store any data in the structs (when its called later it's all zeroes).
Ideas?
The mistake is with your fscanf function . You have to provide FILE pointer (inputFile This context) as first argument and & operator(address of Similar to scanf function) in front of scanning integer and float.
Try this modified fscanf code :-
fscanf(inputFile,"%s%lf%lf%lf%lf%d%lf",SolarSystem[j].Planet_Name,&SolarSystem[j].Fuel, &SolarSystem[j].Velocity, &SolarSystem[j].Height, &SolarSystem[j].Gravity,&SolarSystem[j].Maximum_Thrust, &SolarSystem[j].Difficulty);

C programming error when i redirect the output of a c file to another file

I currently have a file named assign1.c that compiles and runs correctly when I run it using SSH to connect to a remote Linux terminal.
#include <stdio.h>
#define PI 3.141593
int main(){
int degrees = 0;
double radians;
printf("Degrees to Radians \n");
degrees = 0;
radians = degrees*PI/180;
printf("%6i %9.6f \n", degrees, radians);
degrees = 10;
radians = degrees*PI/180;
printf("%6i %9.6f \n", degrees, radians);
while( degrees < 350){
degrees +=10;
radians = degrees*PI/180;
printf("%6i %9.6f \n", degrees, radians);
}
degrees = 360;
radians = degrees*PI/180;
printf("%6i %9.6f \n", degrees, radians);
}
I used ./assign1 > prog1.c to redirect and send the output to a different file prog1.c
Degrees to Radians
0 0.000000
10 0.174533
20 0.349066
30 0.523599
40 0.698132
50 0.872665
60 1.047198
70 1.221731
80 1.396264
90 1.570796
100 1.745329
110 1.919862
120 2.094395
130 2.268928
140 2.443461
150 2.617994
160 2.792527
170 2.967060
180 3.141593
190 3.316126
200 3.490659
210 3.665192
220 3.839725
230 4.014258
240 4.188791
250 4.363324
260 4.537857
270 4.712389
280 4.886922
290 5.061455
300 5.235988
310 5.410521
320 5.585054
330 5.759587
340 5.934120
350 6.108653
360 6.283186
However when I try to compile gcc -o prog1 prog1.c I recieve an error message.
prog1.c:1:1: error: unknown type name âDegreesâ
Degrees to Radians
^
prog1.c:1:12: error: expected â=â, â,â, â;â, âasmâ or â__attribute__â before âRadiansâ
Degrees to Radians
^
I am new to C programming and still having problems understanding the error messages, any one actually understand my error message?
I am a bit confused on what you are trying to achieve, so i'll tell you the full story.
So, you have a program, written in C (i.e. a text file). Since the computer doesn't understand text, we need to translate it in a computer language. So, you have the program assign1.c, you compile that in a executable file (i.e. translate C into a machine-readable form):
gcc -o assign1 assign1.c
Then, you run assign1:
./assign1
, which produces a bunch of output on the stdout (i.e. on the screen). You can write that into a file using a redirection:
./assign1 > prog1.c
Now, the file prog1.c is a simple text file which contains the output produced by your program (the extension is irrelevant). Trying to compile that using gcc is useless, because it is not a valid C program, but rather, it contains the output from your program.
Now, what to do with this file? Well, whatever you want. You can take a look at it:
cat prog1.c
or
less prog1.c
(q to quit from less), or send it to a friend or...whatever.

How to round float numbers in text in C?

So I have this text
today average human lifespan in Western countries is approaching and exceeding 80 years.
1 Japan 82.6 123 19
2 Hong Kong 82.2 234 411
3 Iceland 81.8 345 26
4 Switzerland 81.7 456 7
5 Australia 81.2 567 500
...
80 Lithuania 73.0 800 2
...
194 Swaziland 39.6 142 212
195 133714 18.0 133 998
196 100110011 10.0 667 87351
I need to round the float numbers in this text to whole numbers. I've searched a lot of forums but I cannot seem to find what I need.
This text is given in a .txt file. My task: "Round real number(that have decimals) to whole numbers. The corrected text should be in a new .txt" That's it.
scanf and sscanf are your best friend to extract anything of a string.
floor is use full to suppress decimal on a float. Then can be used to round it (to use it include math.h)...
The format string describes the expected format.The function return the number of parameters found.
Sample:
Initialization
int id = -1;
char country[160]; /* /!\ Warning country name length shall be fewer than 160 */
/* Scanf don't care of this array parameter length. If it is too short */
/* It will erase following memory... */
/* That is why scanf are often disparaging */
float percent = 0.0;
char a_number_as_string[10];
int other_number = -1;
char* Switzerland = "4 Switzerland 81.7654321 456 7";
effectif code
int ret = sscanf(Switzerland, "%d %s %f %s %d", &id, country,
&percent, a_number_as_string, &other_number);
if(ret == 5) {
printf("~~ id: %d\n\tcountry: %s\n\tpercent: %.2f\n\tand : "
"(%s, %d)\n", id, country, percent, a_number_as_string,
other_number);
/////// ROUND
printf("*** round");
printf("\twith printf %%.1f = %.1f\n", percent);
printf("\twith printf %%.2f = %.2f\n", percent);
printf("\twith printf %%.3f = %.3f\n", percent);
printf("\twith printf %%.4f = %.4f\n", percent);
printf("*** With floor (included in math.h)\n");
printf("\t1 decimal: %f\n", floor(percent*10)/10);
printf("\t2 decimal: %f\n", floor(percent*100)/100);
printf("\t3 decimal: %f\n", floor(percent*1000)/1000);
printf("\t4 decimal: %f\n", floor(percent*10000)/10000);
} else {
printf("--> ret = %d", ret);
}
output
~~ id: 4
country: Switzerland
percent: 81.70
and : (456, 7)
*** round
with printf %.1f = 81.8
with printf %.2f = 81.77
with printf %.3f = 81.765
with printf %.4f = 81.7654
*** With floor (included in math.h)
1 decimal: 81.700000
2 decimal: 81.760000
3 decimal: 81.765000
4 decimal: 81.765400
This function are describe in Unix, OSX, Unix terminal man pages:
man scanf
man sscanf
man floor
Or you can find it on several copies of this manages on the web for example
scanf
sscanf
floor
here is the program I have already tested it for a single line of input string:-
// LINK - http://stackoverflow.com/questions/40317323/how-to-extract-float-numbers-from-text-in-c#40317323
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <math.h>
int main()
{
char s[100];
int i,j;
double sum=0.0,frac=0.0;
gets(s); // delimited by '\n' and not by ' '
for( i=0;s[i]!='\0';i++) // for finding index value of decimal point(.)
{
if(s[i]=='.')
break;
}
for(;s[i]!=' ';i--); // for changing key index value to the index value of the first space character(' ') before the decimal point(.)
i++;
for(i;s[i]!='.';i++)
{
sum=sum*10+(s[i]-48); // For extracting integer part
}
i++;
for(i,j=1;s[i]!=' ';i++,j++)
{
frac=frac+(s[i]-48)/pow(10,j); // For extracting fractional part
}
printf("\n\n%lf",sum+frac); // final answer integer part+decimal part
return 0;
}
Explanation:-
okay so what I did is:-
Since scanf() is automatically delimited by space I used gets() which is delimited by new line;
Then we know that there will be a decimal point(.) for floating number in the string, so we find the index value(say key) of the decimal point in the array.
Once we have found the decimal point we know there will only be numbers between the decimal point and the space character after the country name so now we find the index value of that space(key).
Now from that key value we again first move to the decimal point(.) character index while calculating the integer part.Calculated using ASCII value i.e. ASCII value of character Zero(0) is 48 and character Nine(9) is 57 hence subtracting 48 from every character and extracting the value.
Again from the Decimal point(.) to the next space character in the string is part of the floating number and after decimal the numbers follow the weight 10^(-1),10^(-2),10^(-3)...and so on hence the temporary variable and the power() function.Thus we, successfully calculated the fractional part also.
Finally, I just added the Integer and the fractional parts within the printf().
Try, using printf() with all the variables in each of the for loops for better understanding, kinda like dry-run.
You can parse all the values from the string using regex in c#
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Text.RegularExpressions;
using System.Data;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
string[] input = {
"today average human lifespan in Western countries is approaching and exceeding 80 years.",
"1 Japan 82.6 123 19",
"2 Hong Kong 82.2 234 411",
"3 Iceland 81.8 345 26",
"4 Switzerland 81.7 456 7",
"5 Australia 81.2 567 500",
"80 Lithuania 73.0 800 2",
"194 Swaziland 39.6 142 212",
"195 133714 18.0 133 998",
"196 100110011 10.0 667 87351"
};
string pattern = #"(?'index'\d+)\s+(?'country'.*)\s+(?'float'[^ ]+)\s+(?'num1'\d+)\s+(?'num2'\d+)$";
for (int i = 1; i < input.Length; i++)
{
Match match = Regex.Match(input[i], pattern);
Console.WriteLine("index : '{0}', country : '{1}', float : '{2}', num1 : '{3}', num2 : '{4}'",
match.Groups["index"],
match.Groups["country"],
match.Groups["float"],
match.Groups["num1"],
match.Groups["num2"]
);
}
Console.ReadLine();
}
}
}

Rotation algorithm not producing expected results

I am trying to port some code from IDL to C, and I find myself having to replicate the ROT function. The goal is to rotate a 1024x1024 array of unsigned shorts by an angle in degrees. For the purposes of this project, the angle is very small, less than one degree. The function uses bilinear interpolation.
I tried a backwards approach. For each pixel in the output array, I did a reverse rotation to figure out what coordinate in the input array it would belong to, then used interpolation to figure out what that value would be. I wasn't sure how to go about doing bilinear interpolation if the input grid was skewed; every example of it I've seen assumes that it's orthogonal.
For the rotation, I referred to this:
x' = x * cos(a) + y * sin(a)
y' = y * cos(a) - x * sin(a)
from this: Image scaling and rotating in C/C++
And for the interpolation, I referred to this: http://en.wikipedia.org/wiki/Bilinear_interpolation
Anyway, here's my code:
#define DTOR 0.0174532925
void rotatearray(unsigned short int *inarray, unsigned short int *outarray, int xsize,
int ysize, double angle)
{
//allocate temparray, set to 0
unsigned short int *temparray;
temparray = calloc(xsize*ysize, sizeof(unsigned short int));
int xf, yf;
int xi1, xi2, yi1, yi2;
double xi, yi;
double x, y;
double minusangle = (360 - angle)*DTOR;
unsigned short int v11, v12, v21, v22;
int goodpixels=0;
int badpixels=0;
for(yf=0;yf<ysize;yf++)
{
for(xf=0;xf<xsize;xf++)
{
//what point in the input grid would map to this output pixel?
//(inverse of rotation)
xi = (xf+0.5)*cos(minusangle) + (yf+0.5)*sin(minusangle);
yi = (yf+0.5)*cos(minusangle) - (xf+0.5)*sin(minusangle);
//Is it within bounds?
if ((xi>(0+0.5))&&(xi<xsize-0.5)&&
(yi>(0+0.5))&&(yi<ysize-0.5))
{
//what are the indices of the bounding input pixels?
xi1 = (int)(xi - 0.5);
xi2 = (int)(xi + 0.5);
yi1 = (int)(yi - 0.5);
yi2 = (int)(yi + 0.5);
//What position is (x,y) in the bound unit square?
x = xi - xi1;
y = yi - yi1;
//what are the values of the bounding input pixels?
v11 = inarray[yi1*xsize + xi1];//What are the values of
v12 = inarray[yi2*xsize + xi1];//the bounding input pixels?
v21 = inarray[yi1*xsize + xi2];
v22 = inarray[yi2*xsize + xi2];
//Do bilinear interpolation
temparray[yf*xsize + xf] = (unsigned short int)
(v11*(1-x)*(1-y) + v21*x*(1-y) + v12*(1-x)*y + v22*x*y);
goodpixels++;
}
else{temparray[yf*xsize + xf]=0; badpixels++;}
}
}
//copy to outarray
for(yf=0;yf<ysize;yf++)
{
for(xf=0;xf<xsize;xf++)
{
outarray[yf*xsize + xf] = temparray[yf*xsize+xf];
}
}
free(temparray);
return;
}
I tested it by printing several dozen numbers, and comparing it to the same ind of the IDL code, and the results are not at all the same. I'm not sure what more information I can give on that, as I'm not currently able to produce a working image of the array. Do you see any errors in my implementation? Is my reasoning behind the algorithm sound?
EDIT: Here are some selected numbers from the input array; they are identical in the C and IDL programs. What's printed is the x index, followed by the y index, followed by the value at that point.
0 0 24.0000
256 0 17.0000
512 0 23.0000
768 0 21.0000
1023 0 0.00000
0 256 19.0000
256 256 459.000
512 256 379.000
768 256 191.000
1023 256 0.00000
0 512 447.000
256 512 388.000
512 512 231.000
768 512 231.000
1023 512 0.00000
0 768 286.000
256 768 378.000
512 768 249.000
768 768 205.000
1023 768 0.00000
0 1023 6.00000
256 1023 10.0000
512 1023 11.0000
768 1023 12.0000
1023 1023 0.00000
This is what the IDL program outputs after rotation:
0 0 31.0000
256 0 20.4179
512 0 20.3183
768 0 20.0000
1023 0 0.00000
0 256 63.0000
256 256 457.689
512 256 392.406
768 256 354.140
1023 256 0.00000
0 512 511.116
256 512 402.241
512 512 230.939
768 512 240.861
1023 512 0.00000
0 768 296.826
256 768 377.217
512 768 218.039
768 768 277.194
1023 768 0.00000
0 1023 14.0000
256 1023 8.00000
512 1023 9.34906
768 1023 23.7820
1023 1023 0.00000
And here is the data after rotation using my function:
[0,0]: 0
[256,0]: 44
[512,0]: 276
[768,0]: 299
[1023,0]: 0
[0,256]: 0
[256,256]: 461
[512,256]: 439
[768,256]: 253
[1023,256]: 0
[0,512]: 0
[256,512]: 377
[512,512]: 262
[768,512]: 379
[1023,512]: 0
[0,768]: 0
[256,768]: 340
[512,768]: 340
[768,768]: 198
[1023,768]: 18
[0,1023]: 0
[256,1023]: 0
[512,1023]: 0
[768,1023]: 0
[1023,1023]: 0
I didn't see an immediately useful pattern emerging here to indicate what's going on, which is why I didn't originally include it.
EDIT EDIT EDIT: I believe my mind just suddenly stumbled across the problem! I noticed that the 0,0 pixel never seems to change, and that the 1023,1023 pixel changes the most. Of course this means the algorithm is designed to rotate around the origin, while I'm assuming that the function I seek to imitate is designed to rotate around the center of the image. The answer is still not the same but it is much closer. All I did was change the line
xi = (xf+0.5)*cos(minusangle) + (yf+0.5)*sin(minusangle);
yi = (yf+0.5)*cos(minusangle) - (xf+0.5)*sin(minusangle);
to
xi = (xf-512+0.5)*cos(minusangle) + (yf-512+0.5)*sin(minusangle) + 512;
yi = (yf-512+0.5)*cos(minusangle) + (xf-512+0.5)*sin(minusangle) + 512;

sscanf not detecting the right numbers

I'm having a hard time using sscanf to scan hour and minutes from a list. Below is a small snip of the list.
1704 86 2:30p 5:50p Daily
1711 17 10:40a 2:15p 5
1712 86 3:10p 6:30p 1
1731 48 6:25a 9:30a 156
1732 100 10:15a 1:30p Daily
1733 6 2:15p 3:39p Daily
I've tried this, but it keeps getting me segmentation Fault.(I'm putting this information into structures).
for(i=0;i<check_enter;i++){
sscanf(all_flights[i],
"%d %d %d:%d%c %d:%d%c %s",
&all_flights_divid[i].flight_number,
&all_flights_divid[i].route_id,
&all_flights_divid[i].departure_time_hour,
&all_flights_divid[i].departure_time_minute,
&all_flights_divid[i].departure_time_format,
&all_flights_divid[i].arrival_time_minute,
&all_flights_divid[i].arrival_time_minute,
&all_flights_divid[i].arrival_time_format,
&all_flights_divid[i].frequency);
printf("%d ",all_flights_divid[i].flight_number);
printf("%d ",all_flights_divid[i].route_id);
printf("%d ",all_flights_divid[i].departure_time_hour);
printf("%d ",all_flights_divid[i].departure_time_minute);
printf("%c ",all_flights_divid[i].departure_time_format);
printf("%d ",all_flights_divid[i].arrival_time_hour);
printf("%d ",all_flights_divid[i].arrival_time_minute);
printf("%c ",all_flights_divid[i].arrival_time_format);
printf("%s\n",all_flights_divid[i].frequency);
}
This is how I declared it.
struct all_flights{
int flight_number;
int route_id;
int departure_time_hour;
int departure_time_minute;
char departure_time_format;
int arrival_time_hour;
int arrival_time_minute;
char arrival_time_format;
char frequency[10];
};
struct all_flights all_flights_divid[3000];
These are the results I get
1704 86 2 30 p 0 50 p Daily
1711 17 10 40 a 0 15 p 5
1712 86 3 10 p 0 30 p 1
1731 48 6 25 a 0 30 a 156
1732 100 10 15 a 0 30 p Daily
1733 6 2 15 p 0 39 p Daily
Small mistake, that might be the problem:
this:
&all_flights_divid[1].flight_number,
should be:
&all_flights_divid[i].flight_number,
// ^
Edit:
Also, you read arrival_time_minute twice, and not reading arrival_time_hour at all. Fix it and it should be OK.
Most of the results seem to be fine, except the first field.
Now if you check your code..
&all_flights_divid[1]
fix it with
&all_flights_divid[i]

Resources