int main(int argc, char *argv[]) {
  const int n = atoi(argv[1]);
  const int bits_per_bucket = atoi(argv[2]);
  const int total_bits = sizeof(uint64)*8;
  
  const int n_buckets = 1 << bits_per_bucket;
  const int mask = ~((~0) << bits_per_bucket);

  uint64 *a =  random_data(n);
  uint64 *a_sorted =  (uint64*)malloc(sizeof(uint64)*n);

  int *count = (int*)malloc(sizeof(int)*n_buckets);
  int *prefix_sum = (int*)malloc(sizeof(int)*n_buckets);

  float mt1 = omp_get_wtime();
  
  for (int offset = 0; offset < total_bits; offset += bits_per_bucket) {
    for (int i = 0; i < n_buckets; i++) {
      count[i] = 0;
    }
    
    //count number of element that goes in each bucket
    for (int i = 0; i < n; i++) {
      count[ get_bucket_num(a[i], offset, mask) ]++;
    }
    
    //calculate the prefix sum i.e. where each bucket starts
    prefix_sum[0] = 0;
    for (int i = 1; i < n_buckets; i++) {
      prefix_sum[i] = prefix_sum[i-1] + count[i-1];
    }
    
    //put the elements in the right position using the prefix_sum array to store the next index
    for (int i = 0; i < n; i++) {
      int *pos = &prefix_sum[ get_bucket_num(a[i], offset, mask) ];
      a_sorted[*pos] = a[i];
      (*pos)++; 
    }
    
    uint64 *tmp = a;
    a = a_sorted;
    a_sorted = tmp;
  }
  
  uint64 *tmp = a;
  a = a_sorted;
  a_sorted = tmp;
  
  float mt2 = omp_get_wtime();
  float time = mt2-mt1;
  
  for (int i = 1; i < n; i++) {
    if (a_sorted[i-1] > a_sorted[i]) {
      printf("not sorted");
      return 1;
    }
  }

  /*R*/ printf("%d,%d,%d,%f\n", 1, n, bits_per_bucket, time);
}
int main(int argc, char *argv[]) {
    srand((int)time(NULL));
    address_initialization();
    account_register_toBank();
    int balance = eCent_balance();
    if (balance == 0) {
        printf("Balance is equal to 0, get 50 from the bank.\n");
        eCent_get(50);
    }else {
        printf("eCent Balance: %d\n", balance);
    }
    int available_result = list_available();
    if (available_result != 0) {
        return 1;
    }
    //generate the data.
    char rand_data[DATA_LENGTH+1];
    rand_data[0] = '\0';
    random_data(rand_data);
    //before the final step start, call the bank to transfer the eCent.
    int transfer_result = eCent_transfer_toAnalysis();
    if (transfer_result != 0) {
        return transfer_result;
    }
    int analysis_result = request_analysis(rand_data);
    if (analysis_result != 0)
    {
        return analysis_result;
    }
    return 0;
}
int main(int argc, char *argv[]) {
  srand(time(NULL));
  const int dim = atoi(argv[1]);
  const int limit = atoi(argv[2]);
  const int levels = log2(dim)-log2(limit);
  
  g_tmp1 = alloc_temp_matrices(dim, levels);
  g_tmp2 = alloc_temp_matrices(dim, levels);
  
  block a = { 0, 0, random_data(dim) };
  block b = { 0, 0, random_data(dim) };
  block c = { 0, 0, random_data(dim) };
  
  double start = MPI_Wtime();
  multiply(&a, &b, &c, limit, dim, 0);
  double end = MPI_Wtime();
  
  /*R*/ printf("%d,%f\n", levels, end-start);
}
示例#4
0
int main(int argc, char **argv)
{
    int s;
    struct sockaddr_in addr;
    char buffer[BUFFER_SIZE];
	int fd = -1;
	ssize_t size = 0;
	ssize_t nsendsize = 0;

	fd = open("video_cmmb.h264",O_RDONLY); 
	if(fd < 0) {
		perror("open file error!\n");
		return -1;
	}

    if((s = socket(AF_INET,SOCK_STREAM,0)) < 0) {
        perror("socket");
       	return -1;
    }
  
    bzero(&addr,sizeof(addr));
    addr.sin_family = AF_INET;
    addr.sin_port = htons(PORT);
    addr.sin_addr.s_addr = inet_addr(SERVER_IP);
 
    if(connect(s,(struct sockaddr *)&addr,sizeof(addr))<0) {
        perror("connect");
		return -1;
    }
  
    recv(s,buffer,sizeof(buffer),0);
    printf("%s\n",buffer);

    while(1) {
        bzero(buffer, BUFFER_SIZE);

        size = read(fd, buffer, random_data());
		if(size <= 0)
			break;

        if((nsendsize = sendn(s, buffer, size, 0)) < 0) {
		    perror("sendn error!\n");
		    lseek(fd, -size, SEEK_CUR);
		    return -1;
		}

		if(nsendsize < size)
		    lseek(fd, nsendsize - size, SEEK_CUR);

		usleep(1000);
    }

	return 0;
}
void parameter_cloud(Tree &T, Model &Mod, long Nrep, long length, double eps, Parameters &Parsim){

  long iter;

  float likel;


  Parameters Par;
  Alignment align;
  Counts data;

  double eps_pseudo = 0.001;     // Amount added to compute the pseudo-counts.

  // Initialize the parameters for simulation of K81 data for testing
  Par = create_parameters(T);

  // Obtaining the distribution of estimated parameters with EM

  std::ofstream estpar;
  estpar.open("est-par.dat", std::ios::out);
  estpar.precision(15);

  std::vector<double> param;
  for (iter=0; iter < Nrep; iter++) {
    random_data(T, Mod, Parsim, length, align);
    get_counts(align, data);
    add_pseudocounts(eps_pseudo, data);

    // Runs EM
    std::tie(likel, iter)= EMalgorithm(T, Mod, Par, data, eps);

    // Choses the best permutation.
    guess_permutation(T, Mod, Par);

    get_free_param_vector(T, Mod, Par, param);

    for (unsigned long k=0; k < param.size(); k++) {
      estpar << param[k] << "  ";
    }
    estpar << std::endl;
  }

}
示例#6
0
static void bacast_signed_message()
{
        msg_header_t* header;
        uint8_t* data;
        packetbuf_clear();
        header = ( msg_header_t* ) ( packetbuf_dataptr() );
        data = ( uint8_t* ) ( header + 1 );

        random_data ( data, MSG_LEN );

        hton_uint16 ( &header->data_len, MSG_LEN );

	static struct etimer nrg;
	energest_flush();
        ENERGEST_ON ( ENERGEST_TYPE_LPM );
        ENERGEST_ON ( ENERGEST_TYPE_TRANSMIT );
        ENERGEST_ON ( ENERGEST_TYPE_LISTEN );
        ENERGEST_ON ( ENERGEST_TYPE_CPU );
        last.cpu = energest_type_time ( ENERGEST_TYPE_CPU )/RTIMER_SECOND;
        ENERGEST_OFF ( ENERGEST_TYPE_CPU );
        last.lpm = energest_type_time ( ENERGEST_TYPE_LPM );
        last.transmit = energest_type_time ( ENERGEST_TYPE_TRANSMIT );
        last.listen = energest_type_time ( ENERGEST_TYPE_LISTEN );
        ENERGEST_ON ( ENERGEST_TYPE_CPU );

        ecdsa_sign ( data, MSG_LEN, header->r, header->s, prKey_alice );

        diff.cpu = energest_type_time ( ENERGEST_TYPE_CPU ) - last.cpu;
        diff.lpm = energest_type_time ( ENERGEST_TYPE_LPM ) - last.lpm;
        diff.transmit = energest_type_time ( ENERGEST_TYPE_TRANSMIT ) - last.transmit;
        diff.listen = energest_type_time ( ENERGEST_TYPE_LISTEN ) - last.listen;

        ENERGEST_OFF ( ENERGEST_TYPE_CPU );
        ENERGEST_OFF ( ENERGEST_TYPE_LPM );
        ENERGEST_OFF ( ENERGEST_TYPE_TRANSMIT );
        ENERGEST_OFF ( ENERGEST_TYPE_LISTEN );

        packetbuf_set_datalen ( sizeof ( msg_header_t ) + MSG_LEN );
        abc_send ( &abc );
	printf ( "Clock ticks recorded by\nCPU = %ld \nLPM = %ld \nTRANSMITTER = %ld\nRECEIVER = %ld\n",diff.cpu, diff.lpm, diff.transmit, diff.listen );
}
int main(void)
{
  int data[N];
  int i, j;
  int temp;
  random_data(data, N);

  for (i = 0; i < N; i++) {
    temp = data[0];
    for (j = 0; j < i; j++) {
      if (data[temp] < data[j])
        data[j + 1] = data[j];
      else
        break;
    }
    data[j + 1] = data[temp]; 
  }

  print_data(data, N);

  return 0;
}
int
main()
{
  gsl_rng *r = gsl_rng_alloc(gsl_rng_default);
  const double tol1 = 1.0e-8;
  const double tol2 = 1.0e-3;

  gsl_ieee_env_setup();

  {
    const size_t N = 2000000;
    double *data = random_data(N, r);
    double data2[] = { 4.0, 7.0, 13.0, 16.0 };
    size_t i;

    test_basic(2, data, tol1);
    test_basic(100, data, tol1);
    test_basic(1000, data, tol1);
    test_basic(10000, data, tol1);
    test_basic(50000, data, tol1);
    test_basic(80000, data, tol1);
    test_basic(1500000, data, tol1);
    test_basic(2000000, data, tol1);

    for (i = 0; i < 4; ++i)
      data2[i] += 1.0e9;

    test_basic(4, data2, tol1);

    free(data);
  }

  {
    /* dataset from Jain and Chlamtac paper */
    const size_t n_jain = 20;
    const double data_jain[] = {  0.02,  0.15,  0.74,  3.39,  0.83,
                                  22.37, 10.15, 15.43, 38.62, 15.92,
                                  34.60, 10.28,  1.47,  0.40,  0.05,
                                  11.39,  0.27,  0.42,  0.09, 11.37 };
    double expected_jain = 4.44063435326;
  
    test_quantile(0.5, data_jain, n_jain, expected_jain, tol1, "jain");
  }

  {
    size_t n = 1000000;
    double *data = malloc(n * sizeof(double));
    double *sorted_data = malloc(n * sizeof(double));
    gsl_rstat_workspace *rstat_workspace_p = gsl_rstat_alloc();
    double p;
    size_t i;

    for (i = 0; i < n; ++i)
      {
        data[i] = gsl_ran_gaussian_tail(r, 1.3, 1.0);
        gsl_rstat_add(data[i], rstat_workspace_p);
      }

    memcpy(sorted_data, data, n * sizeof(double));
    gsl_sort(sorted_data, 1, n);

    /* test quantile calculation */
    for (p = 0.1; p <= 0.9; p += 0.1)
      {
        double expected = gsl_stats_quantile_from_sorted_data(sorted_data, 1, n, p);
        test_quantile(p, data, n, expected, tol2, "gauss");
      }

    /* test mean, variance */
    {
      const double expected_mean = gsl_stats_mean(data, 1, n);
      const double expected_var = gsl_stats_variance(data, 1, n);
      const double expected_sd = gsl_stats_sd(data, 1, n);
      const double expected_skew = gsl_stats_skew(data, 1, n);
      const double expected_kurtosis = gsl_stats_kurtosis(data, 1, n);
      const double expected_median = gsl_stats_quantile_from_sorted_data(sorted_data, 1, n, 0.5);

      const double mean = gsl_rstat_mean(rstat_workspace_p);
      const double var = gsl_rstat_variance(rstat_workspace_p);
      const double sd = gsl_rstat_sd(rstat_workspace_p);
      const double skew = gsl_rstat_skew(rstat_workspace_p);
      const double kurtosis = gsl_rstat_kurtosis(rstat_workspace_p);
      const double median = gsl_rstat_median(rstat_workspace_p);

      gsl_test_rel(mean, expected_mean, tol1, "mean");
      gsl_test_rel(var, expected_var, tol1, "variance");
      gsl_test_rel(sd, expected_sd, tol1, "stddev");
      gsl_test_rel(skew, expected_skew, tol1, "skew");
      gsl_test_rel(kurtosis, expected_kurtosis, tol1, "kurtosis");
      gsl_test_abs(median, expected_median, tol2, "median");
    }

    free(data);
    free(sorted_data);
    gsl_rstat_free(rstat_workspace_p);
  }

  gsl_rng_free(r);

  exit (gsl_test_summary());
}
void parameter_test(Tree &T, Model &Mod, long Nrep, long length, double eps, std::vector<double> &pvals, std::string data_prefix, bool save_mc_exact){

  long iter;
  long i, r;

  double df, C;
  double distance, KL;
	KL=0;
	distance=0;
  double likel;


  Parameters Parsim, Par, Par_noperm;
  Alignment align;
  Counts data;

  double eps_pseudo = 0.001;     // Amount added to compute the pseudo-counts.

  StateList sl;

  bool save_data = (data_prefix != "");


  std::string output_filename;
  std::stringstream output_index;
  std::ofstream logfile;
  std::ofstream logdistfile;

  std::ofstream out_chi2;
  std::ofstream out_br;
  std::ofstream out_brPerc;

  std::ofstream out_pvals;
  std::ofstream out_pvals_noperm;
  std::ofstream out_qvals;
  std::ofstream out_bound;
  std::ofstream out_variances;
  std::ofstream out_qvalsComb;
  std::ofstream out_qvalsCombzscore;
  std::ofstream out_covmatrix;

  std::ofstream out_parest;
  std::ofstream out_parsim;

  std::vector<double> KLe;
  std::vector<std::vector<double> > chi2_array; // an array of chi2 for every edge.
  std::vector<std::vector<double> > mult_array; // an array of mult for every edge.
  std::vector<std::vector<double> > br_array; // an array of br. length for every edge.
  std::vector<std::vector<double> > br_arrayPerc; // an array of br. length for every edge.

  std::vector<std::vector<double> > cota_array; // an array of upper bounds of the diff in lengths for every edge.
  std::vector<std::vector<double> > pval_array; // an array of pvals for every edge.
  std::vector<std::vector<double> > pval_noperm_array;
  std::vector<std::vector<double> > qval_array; // an array of qvalues for every edge.
  std::vector<std::vector<double> > variances_array; // an array of theoretical variances.
  std::vector<std::vector<double> > parest_array; // array of estimated parameters
  std::vector<std::vector<double> > parsim_array; // array of simulation parameters

	//  ci_binom ci_bin; // condfidence interval
  std::vector<std::vector<ci_binom> > CIbinomial ; //  	vector of CIs

  std::list<long> produced_nan;

  long npars = T.nedges*Mod.df + Mod.rdf;

  // Initializing pvals
  pvals.resize(T.nedges);

  // Initialize the parameters for simulation of K81 data for testing
  Par = create_parameters(T);
  Parsim = create_parameters(T);

  // Initializing data structures
  KLe.resize(T.nedges);

	pval_array.resize(T.nedges);
        pval_noperm_array.resize(T.nedges);
        qval_array.resize(T.nedges);
	chi2_array.resize(T.nedges);
	mult_array.resize(T.nedges);
	br_array.resize(T.nedges);
        br_arrayPerc.resize(T.nedges);
	cota_array.resize(T.nedges);
        variances_array.resize(npars);
        parest_array.resize(npars);
        parsim_array.resize(npars);

	// initialize to 0's
  for (i=0; i < T.nedges; i++) {
      pval_array[i].resize(Nrep, 0);
      pval_noperm_array[i].resize(Nrep, 0);
      qval_array[i].resize(Nrep, 0);
          chi2_array[i].resize(Nrep, 0);
	  mult_array[i].resize(Nrep, 0);
	  br_array[i].resize(Nrep, 0);
          br_arrayPerc[i].resize(Nrep, 0);
	  cota_array[i].resize(Nrep, 0);
  }

  for(i=0; i < npars; i++) {
    variances_array[i].resize(Nrep, 0);
    parest_array[i].resize(Nrep, 0);
    parsim_array[i].resize(Nrep, 0);
  }

  // Information about the chi^2.
  df = Mod.df;
  C = get_scale_constant(Mod);


  if (save_data) {
    logfile.open((data_prefix + ".log").c_str(), std::ios::out);
    logfile << "model:  " << Mod.name << std::endl;
    logfile << "length: " << length << std::endl;
    logfile << "eps:    " << eps << std::endl;
    logfile << "nalpha: " << T.nalpha << std::endl;
    logfile << "leaves: " << T.nleaves << std::endl;
    logfile << "tree:   " << T.tree_name << std::endl;
    logfile << std::endl;
    logdistfile.open((data_prefix + ".dist.log").c_str(), std::ios::out);

    out_chi2.open(("out_chi2-" + data_prefix + ".txt").c_str(), std::ios::out);
    out_br.open(("out_br-" + data_prefix + ".txt").c_str(), std::ios::out);
    out_brPerc.open(("out_brPerc-" + data_prefix + ".txt").c_str(), std::ios::out);
    out_pvals.open(("out_pvals-" + data_prefix + ".txt").c_str(), std::ios::out);
    out_pvals_noperm.open(("out_pvals_noperm-" + data_prefix + ".txt").c_str(), std::ios::out);
    out_qvals.open(("out_qvals-" + data_prefix + ".txt").c_str(), std::ios::out);
    out_variances.open(("out_variances-" + data_prefix + ".txt").c_str(), std::ios::out);
    out_parest.open(("out_params-est-" + data_prefix + ".txt").c_str(), std::ios::out);
    out_parsim.open(("out_params-sim-" + data_prefix + ".txt").c_str(), std::ios::out);
    out_bound.open(("out_bound-" + data_prefix + ".txt").c_str(), std::ios::out);
    out_qvalsComb.open(("out_qvalsComb-" + data_prefix + ".txt").c_str(), std::ios::out);
    out_qvalsCombzscore.open(("out_qvalsCombzscore-" + data_prefix + ".txt").c_str(), std::ios::out);

    out_parsim.precision(15);
    out_parest.precision(15);
    out_variances.precision(15);
  }


	// uncomment the 2 following lines if want to fix the parameters
	// random_parameters_length(T, Mod, Parsim);
	 //random_data(T, Mod, Parsim, length, align);

  for (iter=0; iter < Nrep; iter++) {
    std::cout << "iteration: " << iter << "             \n";

    // Produces an alignment from random parameters
    random_parameters_length(T, Mod, Parsim);


    random_data(T, Mod, Parsim, length, align);
    get_counts(align, data);
    add_pseudocounts(eps_pseudo, data);

    // Saving data
    if (save_data) {
      output_index.str("");
      output_index << iter;
      output_filename = data_prefix + "-" + output_index.str();
      save_alignment(align, output_filename + ".fa");
      save_parameters(Parsim, output_filename + ".sim.dat");
    }

    // Runs the EM
    std::tie(likel, iter) = EMalgorithm(T, Mod, Par, data, eps);

    // If algorithm returns NaN skip this iteration.
    if (boost::math::isnan(likel)) {
      produced_nan.push_back(iter);
      continue;
    }
    copy_parameters(Par, Par_noperm);

    // Chooses the best permutation.
    guess_permutation(T, Mod, Par);

    distance = parameters_distance(Parsim, Par);

      // estimated counts: Par ; original: Parsim
      std::vector<double> counts_est;
      counts_est.resize(T.nalpha, 0);


      // calculate the cov matrix
      std::vector<std::vector<double> > Cov;
      Array2 Cov_br;

      full_MLE_covariance_matrix(T, Mod, Parsim, length, Cov);

      if(save_data) {
          save_matrix(Cov, output_filename + ".cov.dat");
      }

      // Save the covariances in an array
      std::vector<double> param;
      std::vector<double> param_sim;

      param.resize(npars);
      param_sim.resize(npars);

      get_free_param_vector(T, Mod, Par, param);
      get_free_param_vector(T, Mod, Parsim, param_sim);

      for(i=0; i < npars; i++) {
	variances_array[i][iter] = Cov[i][i];
        parsim_array[i][iter] = param_sim[i];
        parest_array[i][iter] = param[i];
      }

      std::vector<double> xbranca, xbranca_noperm, mubranca;
      double chi2_noperm;
      xbranca.resize(Mod.df);
      xbranca_noperm.resize(Mod.df);
      mubranca.resize(Mod.df);
      for (i=0; i < T.nedges; i++) {
		  r = 0; // row to be fixed
		  // Extracts the covariance matrix, 1 edge

				  branch_inverted_covariance_matrix(Mod, Cov, i, Cov_br);
                  get_branch_free_param_vector(T, Mod, Parsim, i, mubranca);
                  get_branch_free_param_vector(T, Mod, Par, i, xbranca);
                  get_branch_free_param_vector(T, Mod, Par_noperm, i, xbranca_noperm);

			      chi2_array[i][iter] = chi2_mult(mubranca, xbranca, Cov_br);
                  chi2_noperm = chi2_mult(mubranca, xbranca_noperm, Cov_br);


                  pval_array[i][iter] =  pvalue_chi2(chi2_array[i][iter], Mod.df);
                  pval_noperm_array[i][iter] = pvalue_chi2(chi2_noperm, Mod.df);

			      br_array[i][iter] = T.edges[i].br - branch_length(Par.tm[i], T.nalpha);
				  br_arrayPerc[i][iter] = branch_length(Par.tm[i], T.nalpha)/T.edges[i].br;


		// Upper bound on the parameter distance using multinomial:
		//  cota_array[i][iter] = bound_mult(Parsim.tm[i], Xm, length);
	    // and using the  L2 bound
		  cota_array[i][iter] = branch_length_error_bound_mult(Parsim.tm[i], Par.tm[i]);
		  out_br <<  br_array[i][iter]  << " ";
		  out_brPerc <<  br_arrayPerc[i][iter]  << " ";

		  out_bound  <<  cota_array[i][iter] << " ";
		  out_chi2 << chi2_array[i][iter] << " ";

			}
         out_chi2 << std::endl;
		 out_bound  <<  std::endl;
		 out_br << std::endl;
		 out_brPerc << std::endl;




    // Saves more data.
    if (save_data) {
      logfile << iter << ": " << distance << "   " << KL << std::endl;
      save_parameters(Par, output_filename + ".est.dat");

      logdistfile << iter << ": ";
      logdistfile << parameters_distance_root(Par, Parsim) << " ";
      for(int j=0; j < T.nedges; j++) {
        logdistfile << parameters_distance_edge(Par, Parsim, j) << " ";
      }
      logdistfile << std::endl;
    }

} // close iter loop here

  // Correct the p-values
  for(i=0; i < T.nedges; i++) {
       BH(pval_array[i], qval_array[i]);
	//save them
  }

  if (save_mc_exact) {
    for(long iter=0; iter < Nrep; iter++) {
      for(long i=0; i < T.nedges; i++) {
        out_pvals << pval_array[i][iter] << "  ";
        out_pvals_noperm << pval_noperm_array[i][iter] << "  ";
        out_qvals << qval_array[i][iter] << "  ";
      }
      out_pvals  << std::endl;
      out_pvals_noperm << std::endl;
      out_qvals  << std::endl;

      for(long i=0; i < npars; i++) {
        out_variances << variances_array[i][iter] << "  ";
        out_parsim << parsim_array[i][iter] << "  ";
        out_parest << parest_array[i][iter] << "  ";
      }
      out_variances << std::endl;
      out_parsim << std::endl;
      out_parest << std::endl;
    }
  }

	// now combine the pvalues
   for(i=0; i < T.nedges; i++) {
	pvals[i] = Fisher_combined_pvalue(pval_array[i]);
    //using the Zscore it goes like this: pvals[i] = Zscore_combined_pvalue(pval_array[i]);
	if (save_mc_exact) {	   out_qvalsComb <<  pvals[i] << "  " ;
	out_qvalsCombzscore << Zscore_combined_pvalue(pval_array[i]) << " ";
	}
  }

  // Close files
  if (save_data) {
    logdistfile.close();
    logfile.close();
  }

if (save_mc_exact) {
	out_chi2.close();
	out_bound.close();
        out_variances.close();
        out_parest.close();
        out_parsim.close();
	out_br.close();
	out_brPerc.close();

	out_pvals.close();
        out_qvals.close();
	out_qvalsComb.close();
	out_qvalsCombzscore.close();
        out_covmatrix.close();
	}

  // Warn if some EM's produced NaN.
  if (produced_nan.size() > 0) {
    std::cout << std::endl;
    std::cout << "WARNING: Some iterations produced NaN." << std::endl;
    std::list<long>::iterator it;
    for (it = produced_nan.begin(); it != produced_nan.end(); it++) {
      std::cout << *it << ", ";
    }
    std::cout << std::endl;
  }
}
示例#10
0
   int main(int argn, char *argv[])
   {
      int type_data;
      int type_tri;
      int sauvegarde_tableau_initial;
      int sauvegarde_tableau_final;
      int affichage_tableaux;
      int n = 0;
      char *fichier_lecture_tableau_initial, *fichier_sauvegarde_tableau_initial, *fichier_sauvegarde_tableau_final;
      int *tab;
      int i;
   
   
      structSondes sondes = {0, 0, 0};
   
      if (argn == 1) 
      {
         aide(argv[0]);
         exit(1);
      }
   
      type_data = UNKNOWN;
      type_tri = UNKNOWN;
      sauvegarde_tableau_initial = FALSE;
      sauvegarde_tableau_final = FALSE;
      affichage_tableaux = FALSE;
   
      for ( i = 1; i < argn; i+=2 )
      {
      	// choix des données à trier et des sauvegardes éventuelles du tableau initial et final
         if (strcmp("-f", argv[i]) == 0)
         {
            fichier_lecture_tableau_initial = (char *) malloc(1 + strlen(argv[i+1]) * sizeof(char));
            strcpy(fichier_lecture_tableau_initial, argv[i+1]);
            type_data = FICHIER;
            continue;
         }
      
         if (strcmp("-si", argv[i]) == 0)
         {
            fichier_sauvegarde_tableau_initial = (char *) malloc(1 + strlen(argv[i+1]) * sizeof(char));
            strcpy(fichier_sauvegarde_tableau_initial, argv[i+1]);
            sauvegarde_tableau_initial = TRUE;
            continue;
         }
      
         if (strcmp("-sf", argv[i]) == 0)
         {
            fichier_sauvegarde_tableau_final = (char *) malloc(1 + strlen(argv[i+1]) * sizeof(char));
            strcpy(fichier_sauvegarde_tableau_final, argv[i+1]);
            sauvegarde_tableau_final = TRUE;
            continue;
         }
      
         if (strcmp("-a", argv[i]) == 0)
         {
            n = atoi(argv[i+1]);
            type_data = RANDOM;
            continue;
         }
      
         if (strcmp("-mc", argv[i]) == 0)
         {
            n = atoi(argv[i+1]);
            type_data = TRIE;
            continue;
         }
      
         if (strcmp("-pc", argv[i]) == 0)
         {
            n = atoi(argv[i+1]);
            type_data = TRIE_INVERSE;
            continue;
         }

      
       	// choix de l'algorithme de tri
         if (strcmp("-t", argv[i]) == 0)
         {
            if (strcmp("bulle_naif", argv[i+1]) == 0)
               type_tri = BULLE_NAIF;
            
            else if (strcmp("bulle_bool", argv[i+1]) == 0)
               type_tri = BULLE_BOOL;
            
            else if (strcmp("bulle_opt", argv[i+1]) == 0)
               type_tri = BULLE_OPT;
            
            else if (strcmp("selection", argv[i+1]) == 0)
               type_tri = SELECTION;
            
            else if (strcmp("insertion", argv[i+1]) == 0)
               type_tri = INSERTION;
            
            else if (strcmp("rapide", argv[i+1]) == 0)
               type_tri = TRIRAPIDE;
            	
            else 
            {
					printf("\n le tri demandé < %s >  n'existe pas \n", argv[i+1]);
               aide(argv[0]);
               exit(1);
            }
            continue;
         }

      
       	// choix de la visualisation (affichage) du tableau initial et final
         if (strcmp("-v", argv[i]) == 0)
         {
            affichage_tableaux = TRUE;
            i--;
            continue;
         }
      	
			printf("\n l'option demandée < %s >  n'existe pas \n", argv[i]);
         aide(argv[0]);	
			exit(1);
      }
   
   	if (n < 1) {
			printf("\n le nombre d'éléments à trier est incorrect : %d \n", n);
         aide(argv[0]);	
			exit(1);
		}
   
   
      switch(type_data)
      {
         case TRIE:
            {
               tab = data_triee(n);
               printf("Tableau initial trié (meilleur des cas)");
               break;
            }
         
         case TRIE_INVERSE:
            {
               tab = data_triee_inverse(n);
               printf("Tableau intial trié en ordre inverse (pire des cas)");
               break;
            }
         case FICHIER:
            {
               tab = f_lire_data(fichier_lecture_tableau_initial, &n);
               printf("Tableau initial lu dans %s", fichier_lecture_tableau_initial);
               break;
            }
         case RANDOM:
            {
               tab = random_data(n);
               printf("Tableau initial aléatoire");
               break;
            }
         case UNKNOWN:
            aide(argv[0]);
            exit(1);
      }
   
      if (sauvegarde_tableau_initial == TRUE)
         f_ecrire_data(fichier_sauvegarde_tableau_initial, tab, n);
   
   
      if (affichage_tableaux == TRUE) {
         printf("\n");
         ecrire_data(tab,  n);
      }
   
      switch(type_tri)
      {
         case BULLE_NAIF: 
            sondes = tri_bulle_naif(tab, n);
            if (affichage_tableaux == TRUE) {
               printf("Tableau trié (bulle naïf)\n");
               ecrire_data(tab,  n);
            }
            analyse_complexite(sondes, "bulle naïf", n);
            break;
         case BULLE_BOOL: 
            sondes = tri_bulle_bool(tab, n);
            if (affichage_tableaux == TRUE) {
               printf("Tableau trié (bulle bool)\n");
               ecrire_data(tab,  n);
            }
            analyse_complexite(sondes, "bulle bool", n);
            break;
         case BULLE_OPT: 
            sondes = tri_bulle_opt(tab, n);
            if (affichage_tableaux == TRUE) {
               printf("Tableau trié (bulle opt)\n");
               ecrire_data(tab,  n);
            }
            analyse_complexite(sondes, "bulle opt", n);
            break;
         case SELECTION:
            sondes = tri_selection(tab, n);
            if (affichage_tableaux == TRUE) {
               printf("Tableau trié (selection)\n");
               ecrire_data(tab,  n);
            }
            analyse_complexite(sondes, "selection", n);
            break;
         case INSERTION:
            sondes = tri_insertion(tab, n);
            if (affichage_tableaux == TRUE) {
               printf("Tableau trié (insertion)\n");
               ecrire_data(tab,  n);
            }
            analyse_complexite(sondes, "insertion", n);
            break;
         case TRIRAPIDE:
            sondes = tri_rapide(tab, 0, n-1);
            if (affichage_tableaux == TRUE) {
               printf("Tableau trié (rapide)\n");
               ecrire_data(tab,  n);
            }
            analyse_complexite(sondes, "rapide", n);
            break;
         case UNKNOWN:
            aide(argv[0]);
            exit(1);
      }
   
   
      if (sauvegarde_tableau_final == TRUE)
         f_ecrire_data(fichier_sauvegarde_tableau_final, tab, n);
   
      printf("\n");
      return 0;
   }
int main(int argc, char *argv[]) {
  const int n = atoi(argv[1]);
  const int bits_per_bucket = atoi(argv[2]);
  const int total_bits = sizeof(uint64)*8;
  
  const int n_buckets = 1 << bits_per_bucket;
  const int mask = ~((~0) << bits_per_bucket);

  uint64 *a = random_data(n);
  uint64 *a_sorted =  (uint64*)malloc(sizeof(uint64)*n);


  int num_th;
  float mt1;
  
  #pragma omp parallel
  #pragma omp single
  num_th = omp_get_num_threads();
  
  
  int **count = (int**)malloc(sizeof(int*)*num_th);
  int **prefix_sum = (int**)malloc(sizeof(int*)*num_th);
  for (int i = 0; i < num_th; i++) {
    count[i] = (int*)malloc(sizeof(int)*n_buckets);
    prefix_sum[i] = (int*)malloc(sizeof(int)*n_buckets);
  }
  
  mt1 = omp_get_wtime();
  
  int chunk_size = n > num_th ? ceil(n/(double)num_th) : n;
  
  for (int offset = 0; offset < total_bits; offset += bits_per_bucket) {
    prefix_sum[0][0] = 0;
    
    #pragma omp parallel
    {
      int pid = omp_get_thread_num();
      int start = pid * chunk_size;
      int end = min(start + chunk_size, n);
      
      for (int bucket = 0; bucket < n_buckets; bucket++) {
        count[pid][bucket] = 0;
      }
      
      for (int i = start; i < end; i++) {
        count[pid][ get_bucket_num(a[i], offset, mask) ]++;
      }
      
      #pragma omp barrier
      #pragma omp single
      for (int bucket = 0; bucket < n_buckets; bucket++) {
        if (bucket > 0)
          prefix_sum[0][bucket] = prefix_sum[num_th-1][bucket-1] + count[num_th-1][bucket-1];
        
        for (int th = 1; th < num_th; th++) {
          prefix_sum[th][bucket] = prefix_sum[th-1][bucket] + count[th-1][bucket];
        }
      }
      #pragma omp barrier
      
      for (int i = start; i < end; i++) {
        int *pos = &prefix_sum[pid][get_bucket_num(a[i], offset, mask)];
        a_sorted[*pos] = a[i];
        (*pos)++;
      }
    }
    
    uint64 *tmp = a;
    a = a_sorted;
    a_sorted = tmp;
  }
  
  uint64 *tmp = a;
  a = a_sorted;
  a_sorted = tmp;
  
  
  float mt2 = omp_get_wtime();
  float time = mt2-mt1;

  for (int i = 1; i < n; i++) {
    if (a_sorted[i-1] > a_sorted[i]) {
      printf("not sorted");
      return 1;
    }
  }
  
  /*R*/ printf("%d,%d,%d,%f\n", num_th, n, bits_per_bucket, time);
}