Initializer element is not constant - C - c

I'm getting two errors :
Initializer element is not constant in the 2nd last line below in the code
Expected declaration specifiers '...' before string constant in the last line
#define K 10.0
typedef double (*TFunc)(double);
double alpha,x;
double f(double x)
{
return x*x;
}
double derive(TFunc f, const double x0)
{
const double dx = 1.0e-6; // or similar
double dy = f(x0+dx)-f(x0-dx);
return dy/(2.*dx);
}
double fp = derive(f, K);
printf("%lf\n",fp);

You should add any block of code you want to run first during the execution in to a main function. In your case, you should put the code:
double fp = derive(f, K);
printf("%lf\n",fp);
into a main function
int main() {
double fp = derive(f, K);
printf("%lf\n",fp);
}
Make sure you include the stdio.h library at the beginning of file since you are using printf function. Also, make sure you define constant K somewhere. I updated your code according to my suggestion above and it compiled without errors or warnings:
#include <stdio.h>
typedef double (*TFunc)(double);
double alpha,x;
double f(double x)
{
return x*x;
}
double derive(TFunc f, const double x0)
{
const double dx = 1.0e-6; // or similar
double dy = f(x0+dx)-f(x0-dx);
return dy/(2.*dx);
}
int main() {
const double K = 1.0;
double fp = derive(f, K);
printf("%lf\n",fp);
}

Related

While loop causing function to return 0 in c

I have the following c function working on implementing a rejection sampler. MersenneTwiser.h generates a random number between 0 and 1. The issue I'm having is with the rnorm function. I'm using a while loop to reject some samples. It's nonsense at the moment as it's not finished. In it's current form, the program returns 0.00000.
#include<stdio.h>
#include<math.h>
#include"MersenneTwister.h"
MTRand rng;
double p;
double prop;
int sign;
double dubexp(double theta){
p = rng.rand();
if ((p-0.5) > 0) sign= 1;
if ((p-0.5) < 0) sign= -1;
prop = -(1/theta)*sign*log(1-2*abs(p-0.5));
return(prop);
}
double u;
double theta;
double t;
double z;
double c;
double x;
double rnorm(double theta, double c){
t=rng.rand();
while (z == t)
{
x=dubexp(theta);
u=rng.rand();
z=x;
}
return z;
}
int main(){
theta=1;
c=1;
u = rnorm(theta,c);
printf("%f",u);
}
However if I remove the while loop, it returns the correct value of z. As below:
double rnorm(double theta, double c){
t=rng.rand();
x=dubexp(theta);
u=rng.rand();
z=x;
return z;
}
The while-loop never runs
double rnorm(double theta, double c){
t=rng.rand();
while (z == t) // <-- this condition is never true, so the loop doesn't run and the function just returns z
{
x=dubexp(theta);
u=rng.rand();
z=x;
}
return z;
}
See the comment above.
Also, z is defined globally. Global vars and static vars are initialized to zero. That's the reason.

Pointer Matrix in C

I am trying to execute the following code
static double** updateA(double f_x0,double f_x1,double f_x2){
double a[3][3] = {{f_x0*f_x0, f_x0, 1},{f_x1*f_x1, f_x1, 1},{f_x2*f_x2, f_x2, 1}};
return a;
}
static double** updateAc (double f_x0,double f_x1,double f_x2, double x0,double x1,double x2){
double ac[3][3] = {{f_x0*f_x0, f_x0, x0},{f_x1*f_x1, f_x1, x1},{f_x2*f_x2, f_x2, x2}};
return ac;
}
static double det3x3 (double** a){
return (a[0][0]*((a[1][1]*a[2][2]) - (a[2][1]*a[1][2])) - a[0][1]*(a[1][0]
* a[2][2] - a[2][0]*a[1][2]) + a[0][2]*(a[1][0]*a[2][1] - a[2][0]*a[1][1]));
}
static double newx2 (double f_x0,double f_x1,double f_x2, double x0,double x1,double x2){
double **ac = updateAc(f_x0, f_x1, f_x2, x0, x1, x2);
double **a = updateA(f_x0, f_x1, f_x2);
double c = det3x3(ac)/det3x3(a);
return c;
}
However it is not working, it compiles with the following warning:
incompatible pointer types returning 'double [3][3]' from
a function with result type 'double **'
But when I try to execute the code it doesn't work. I am using gcc as compiler.
Anyone can help me?
Thank you in advance,
Lucas
This is the struct method.
Only works for fixed sizes (in this case : 3*3)
the sizes are hard-coded
the caller (in this case main() allocates, and passes a pointer.
#include <stdio.h>
struct nine {
double data[3][3];
};
void do_it(struct nine *p)
{
p->data[0][0] = 0.0;
// ..
}
int main(void)
{
struct nine this9 = {{{1,2,3},{4,5,6},{7,8,9}}};
do_it( &this9 );
printf("%lf\n", this9.data[0][0] );
return 0;
}

How does typedef with tuples work?

We got this typedef in a homework program. As a programmer noob, I didn't see anything like this before. Does this mean that any DoubleFunction2D is actually a 2-tuple of (double, double)?
Program:
typedefs:
typedef double (*DoubleFunction) (double);
typedef double (*DoubleFunction2D) (double, double);
typedef double (*DoubleFunction3D) (double, double, double);
Example usage
(my WIP solution to a task, not yet complied/tested. Inside):
double expf2D(double x, double y)
{
double r = sqrt(pow(x,2) + pow(y,2));
return my_expf(r);
}
double DiskMonteCarloIntegrator(DoubleFunction2D f, double r1, double r2, int N)
{
bool is_inside_ring(double x, double y){
return is_inside_ellipse(x, y, r2/2, r2/2) && !(is_inside_ellipse(x, y, r1/2, r1/2));
}
int i=0;
double x, y, sum = 0;
while(i < N)
{
x = RandomDouble(-1*r1, r1);
y = RandomDouble(-1*r1, r1);
if(is_inside_ring(x, y))
{
sum += f(x, y);
i++;
}
}
double avg = sum / N;
double integral = avg * (pow(r2, 2) - pow(r1, 2)) * M_PI;
return integral;
}
//extract
void main(int argc, char *argv[]){
DiskMonteCarloIntegrator(expf2D, 1.0, 2.0, 1000000);
}
There are no tuples here (in fact, there are no "tuples" in the C programming language).
typedef double (*DoubleFunction) (double);
means DoubleFunction is a pointer to a function that takes a double and returns a double.
typedef double (*DoubleFunction2D) (double, double);
means DoubleFunction2D is a pointer to a function that takes two double values and returns a double.
typedef double (*DoubleFunction3D) (double, double, double);
means DoubleFunction3D is a pointer to a function that takes three double values and returns a double.

Efficient double integration in C with GSL

Consider the double integral
I = int int [(a^k)*b] da db
where we want to integrate for a between [0,1] and b between [0,1] and k is some constant. I am using the GSL numerical integration library but have a memory allocation issue.
My code is as follows
#include <stdlib.h>
#include <stdlib.h>
#include <math.h>
#include <gsl/gsl_integration.h>
double innerIntegrand(double a, void *params) {
double *cast_params = (double *) params;
double b = params[0];
double k = params[1];
return pow(a,k)*b;
}
I can then evaluate the inner integral for a given b (to get an outer integrand) as follows
double outerIntegrand(double b, void *params) {
// params = {holder for double b, k}
double *cast_params = (double *) params;
cast_params[0] = b;
// Allocate integration workspace
gsl_integration_workspace *giw = gsl_integration_workspace_alloc(100);
// Create GSL function
gsl_function F;
F.function = &innerIntegrand;
F.params = params;
// Initialise values to put the result in
double result;
double abserror;
// Perform integration
gsl_integration_qag(&F, 0, 1, 0.001, 0.001, 100, 1, giw, &result, &abserror);
// Free the integration workspace
gsl_integration_workspace_free(giw);
// Return result
return result
}
Note however I have to allocate and free the integration workspace within the function. This means it is done many times when evaluating the final integration function
double Integral(double k) {
// Create params
double *params = malloc(2*sizeof(double));
params[1] = k;
// Allocate integration workspace
gsl_integration_workspace *giw = gsl_integration_workspace_alloc(100);
// Create GSL function
gsl_function F;
F.function = &outerIntegrand;
F.params = params;
// Initialise values to put the result in
double result;
double abserror;
// Perform integration
gsl_integration_qag(&F, 0, 1, 0.001, 0.001, 100, 1, giw, &result, &abserror);
// Free the integration workspace
gsl_integration_workspace_free(giw);
// Free memory
free(params);
// Return result
return result
}
Ideally what I want is two global gsl_integration_workspace variables, one for the integral in outerIntegrand and another for the integral in Integral. However when I try to declare them as global values I receive a initializer element is not constant error.
Can anyone see a way to do this double integral without the repeated memory allocation and freeing? I was thinking we could also pass the workspace in through the params argument although it then starts to get quite messy.
I managed to build a decently looking program in C++ for double integration based on GSL, avoiding repeated allocations in a clean way. I used this well known function to play:
f(x,y)=exp(-x*x-y*y)
integrating it over all the plane (the result, pi, can easily be obtained by switching to polar coordinates).
It is trivial to modify it and add parameters by lambda capture.
#include <iostream>
#include <gsl/gsl_integration.h>
// Simple RAII wrapper
class IntegrationWorkspace {
gsl_integration_workspace * wsp;
public:
IntegrationWorkspace(const size_t n=1000):
wsp(gsl_integration_workspace_alloc(n)) {}
~IntegrationWorkspace() { gsl_integration_workspace_free(wsp); }
operator gsl_integration_workspace*() { return wsp; }
};
// Build gsl_function from lambda
template <typename F>
class gsl_function_pp: public gsl_function {
const F func;
static double invoke(double x, void *params) {
return static_cast<gsl_function_pp*>(params)->func(x);
}
public:
gsl_function_pp(const F& f) : func(f) {
function = &gsl_function_pp::invoke; //inherited from gsl_function
params = this; //inherited from gsl_function
}
operator gsl_function*(){return this;}
};
// Helper function for template construction
template <typename F>
gsl_function_pp<F> make_gsl_function(const F& func) {
return gsl_function_pp<F>(func);
}
int main() {
double epsabs = 1e-8;
double epsrel = 1e-8;
size_t limit = 100;
double result, abserr, inner_result, inner_abserr;
IntegrationWorkspace wsp1(limit);
IntegrationWorkspace wsp2(limit);
auto outer = make_gsl_function( [&](double x) {
auto inner = make_gsl_function( [&](double y) {return exp(-x*x-y*y);} );
gsl_integration_qagi(inner, epsabs, epsrel, limit, wsp1,
&inner_result, &inner_abserr);
return inner_result;
} );
gsl_integration_qagi(outer, epsabs, epsrel, limit, wsp2, &result, &abserr);
std::cout << result << std::endl;
}
This looks weird:
double innerIntegrand(double a, void *params) {
double *cast_params = (double *) params;
double b = params[0];
double k = params[1];
Is it correct to expect that (void *)param[0] and [1] correctly map to double b and k? How is proper offset to be calculated between void and double types?
Here some hints (do not expect working code below).
You may try something like:
double b = (double )*param;
double k = (double )*(param + sizeof(double));
But probably it would be better and safer to declare:
double Integral(double k) {
struct p {
double b;
double k;
} params;
params.k = k;
...
gsl_function F;
F.function = &outerIntegrand;
F.params = &params;
...
double outerIntegrand(double b, void *params) {
(struct p)params->b = b;
double innerIntegrand(double a, void *params) {
double b = (struct p)params->b;
double k = (struct p)params->k;
You may want to typdef the "struct p".

Getting strange numbers returned from a function in C

I have a couple of files:
evaluate_sin.c:
int evaluate_sin(int deg) {
double j = deg_to_rad(deg);
j = sin(j);
printf("sin(%d) = %d\n", deg, j);
return j;
}
deg_to_rad.c
double deg_to_rad(int deg) {
double rad = (3.14 * deg) / 180;
return rad;
}
When I pass the "deg" variable (which is an integer) in my evaluate_sin function to deg_to_rad j is ends up as some random number like -90503293. Why is this?
Note that j is a double, not an integer
Soprintf("sin(%d) = %d\n", deg, j); should be placed with printf("sin(%d) = %f\n", deg, j);
You've not declared deg_to_rad():
extern double deg_to_rad(int deg);
before you use it. Your code assumes it returns an int and converts that into a double.
You should have a header degtorad.h.
degtorad.h
#ifndef DEGTORAD_H_INCLUDED
#define DEGTORAD_H_INCLUDED
extern double deg_to_rad(int deg);
#endif /* DEGTORAD_H_INCLUDED */
(The header guards aren't 100% necessary in this example, but this is a good basis for more complex cases where the header guards are necessary.)
Then your program files include this header. Somewhere along the line, you need to declare evaluate_sin() too; it could go into the same header.
evaluate_sin.c:
#include <math.h>
#include <stdio.h>
#include "degtorad.h"
double evaluate_sin(int deg)
{
double j = deg_to_rad(deg);
j = sin(j);
printf("sin(%d) = %.6f\n", deg, j);
return j;
}
Note also the change in return type (double instead of int); it will return 0 unless you manage to pass in an exact odd multiple of π/2 (when it would return -1 or +1). And also the change in the format for the double value (%.6f instead of %d, which would print an integer).
If you're using GCC, you need to turn on compilation warnings; at least -Wall.
deg_to_rad.c
#include "deg_to_rad.h"
double deg_to_rad(int deg)
{
double rad = (3.14 * deg) / 180;
return rad;
}
although printf("%f", doubleValue) is okay with doubles, I would still suggest keep it as simple as possible and use the way scanf() requires the %lf for doubles. This gives the program sense of consistency.
so yes I would suggest:
printf("sin(%d) = %lf\n", deg, j);

Resources