@sgnablo forse conviene spostare tutto qui.

Ora il (nuovo) problema.


#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <string.h>

int main(int argc, char const *argv[])
{

FILE *infile;

uint64_t *timestamp;
uint16_t *channel;

timestamp = malloc(8);
channel = malloc(2);


infile = fopen("timestamps_10byte.txt", "rb");
if(!infile) return -1;

fseek(infile, 40, SEEK_SET);

while(feof(infile)!=1){

fread(timestamp, 8, 1, infile);
fread(channel, 2, 1, infile);

printf("%u %u\n", *timestamp, *channel);
getchar();
}

fclose(infile);
return 0;
}


Perché non mi legge channel? :'( :'( :'(
Si 'u ciucciu 'un vò ma viva, avaca ma frischi...

non e' quello il problema, ma usa sizeof invece di hardcodare la dimensione.
J:
unita' 4/1981
comp: 7.99%

No, mi servono 8 e 2 byte rispettivamente.

Comunque ho risolto il problema del channel. O meglio, se li metto in due printf diversi (o se semplicemente li inverto :omg: ) non dà nessun problema...

Ora devo capire se il timestamp che mi hanno passato è stato fatto al buio (cosa che spero) o a laser scoperto (e a quel punto harakiri unica via) :facepalm:
Si 'u ciucciu 'un vò ma viva, avaca ma frischi...

http://en.cppreference.com/w/c/types/integer

CTRL+F PRIu

Comunque probabilmente sarebbe meglio una cosa tipo


uint64_t timestamp;
uint16_t channel;

// [...]

fread(&timestamp, 8, 1, infile);
fread(&channel, 2, 1, infile);
J:
unita' 4/1981
comp: 7.99%

Ok, il codice ora funziona alla perfezione (e mi dice anche quanti conteggi ha preso ogni singolo canale) :mki:


#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <string.h>


//  Returns the size of the input file
size_t fsize(FILE* file)
{
if( !file ) { return 0; }

const size_t curr_position = ftell(file);

fseek(file, 0, SEEK_END);
size_t file_size = ftell(file);
fseek(file, curr_position, SEEK_SET);

return file_size;}

// The program
int main(int argc, char const *argv[])
{

// Initializing filenames
FILE *infile, *outfile, *outsingles;

// Initializing the timestamp and channel pairs
uint64_t timestamp[2];
uint16_t channel[2];

// Initializing the array with the singles counts
uint32_t counts[8];

// Opening the input file
infile = fopen("timestamps_10byte.txt", "rb");
if(!infile) return -1; // Error checking

// Opening the coincidence output file
outfile = fopen("coincidences_binary.dat", "w");

// Defining file_size so that the last few bits will be discarded
// in case they're not exactly 10
size_t file_size = fsize(infile) - 40;
file_size -= file_size % 10;

// Allocating memory to contain the file
uint8_t* data = malloc(sizeof(uint8_t)*file_size);

// Discarding the 40 bytes header
fseek(infile, 40, SEEK_SET);

// Copying the file in memory
fread(data, sizeof(uint8_t), file_size, infile);

// Reading the first timestamp-channel couple
timestamp[0] = *(uint64_t *) &data[0];
channel[0] = *(uint16_t *) &data[8];

// Registering the single count to the right channel
counts[channel[0]]++;


uint64_t curr_byte; // Marker for the following loop

for(int timetag_index = 1;
timetag_index < file_size/10;
timetag_index++){

curr_byte = timetag_index * 10;

// Getting the data
timestamp[1] = *(uint64_t *) &data[curr_byte];
channel[1] = *(uint16_t *) &data[curr_byte+8];

counts[channel[1]]++; // Incrementing the singles count for the channel

//*** Debug lines - Uncomment the following ***
//
//printf("%u, ", *timestamp);
//printf("%u\n", *channel);
//getchar();


if(abs(timestamp[1] - timestamp[0]) < 100) // If a coincidence occurs
{
//*** Debug lines - Uncomment the following ***
//
//printf("%s %u, %u\n", "Coincidence found! Channels: ", channel[0], channel[1]);
//printf("%s %u, ", "Timestamps are: ", timestamp[0]);
//printf("%u\n", timestamp[1]);
//printf("%s %u\n", "Difference is: ", abs(timestamp[1] - timestamp[0]));
//getchar();

// Printing coincidence to file
fprintf(outfile, "%u,", channel[0]+1);
fprintf(outfile, "%u\n", channel[1]+1);
}

timestamp[0] = timestamp[1];
channel[0] = channel[1];

}

fclose(outfile);

// Opening the singles output file
outsingles = fopen("singles.dat","w");

for(int i=0; i<8; i++)
{
fprintf(outsingles,"%u\n", counts[i]); // Writing counts to file
}


fclose(outsingles);
fclose(infile);

return 0;
}



Ora però sorge un problema: se volessi scriverlo anche per le due scatole utilizzando il timestamp binario?  :bye:
Si 'u ciucciu 'un vò ma viva, avaca ma frischi...

colo l'occasione per chiedere all'amministreria una mod per formattare il codice in modo dignitoso :verovero:

È @madnessmike l'esperto di mod
Ritengo di avere diritto alle royalties sull'acronimo BUBS :lki:
Sono scemo di mio :verovero: Tutto a posto | I don't have a problem with caffeine. I have a problem without caffeine.
Se i nostri cervelli fossero abbastanza semplici da poter essere capiti, allora saremmo così semplici che non capiremmo - Ian Stewart
Fotografia ad mentula

スニャブロ ufficiale del forum
pulsantoni pulsantosi per greasemonkey: http://bubs.altervista.org/index.php?topic=4.msg183#msg183
script greasemonkey anti-ads: http://bubs.altervista.org/index.php?topic=6.msg2581#msg2581

I miei vaneggi pseudodisegnosi: http://sgnafp.deviantart.com/

"Speed never killed anyone, suddenly becoming stationary, that's what gets you."

done. Ho messo uno dei temi presenti, ditemi se vi piace. ce ne sono diciottomila :asd:
スニャブロ ufficiale del forum
pulsantoni pulsantosi per greasemonkey: http://bubs.altervista.org/index.php?topic=4.msg183#msg183
script greasemonkey anti-ads: http://bubs.altervista.org/index.php?topic=6.msg2581#msg2581

I miei vaneggi pseudodisegnosi: http://sgnafp.deviantart.com/

"Speed never killed anyone, suddenly becoming stationary, that's what gets you."


peccato che il codice di JM non venga formattato completamente :rp:
スニャブロ ufficiale del forum
pulsantoni pulsantosi per greasemonkey: http://bubs.altervista.org/index.php?topic=4.msg183#msg183
script greasemonkey anti-ads: http://bubs.altervista.org/index.php?topic=6.msg2581#msg2581

I miei vaneggi pseudodisegnosi: http://sgnafp.deviantart.com/

"Speed never killed anyone, suddenly becoming stationary, that's what gets you."


Piunno, si dice piunno .azz.
K, fottiti
Fai contenta la tua tosse, fuma una sigaretta


Ma  :rp:

Neanche una mod decente riescono a fare?
Si 'u ciucciu 'un vò ma viva, avaca ma frischi...

Eniuei, credo di aver fatto un passo avanti col programma delle due scatole.

Se, invece di prendere finestra per finestra, prendessi solo il primo conteggio sui canali 8 come riferimento, potrei copiare in un file tutto quanto con i timestamp "compatibili", ignorando tutti gli altri conteggi sui canali 8. Il problema diventerebbe a questo punto gestire il fatto che ho un flusso di byte, quindi non saprei come lavorare col binario.

E poi rimarrebbe il problema dell'ordinamento, dovendo avere a che fare, appunto, con flussi di byte e non con array.

Idee?
Si 'u ciucciu 'un vò ma viva, avaca ma frischi...

non laurearti :lkof:
スニャブロ ufficiale del forum
pulsantoni pulsantosi per greasemonkey: http://bubs.altervista.org/index.php?topic=4.msg183#msg183
script greasemonkey anti-ads: http://bubs.altervista.org/index.php?topic=6.msg2581#msg2581

I miei vaneggi pseudodisegnosi: http://sgnafp.deviantart.com/

"Speed never killed anyone, suddenly becoming stationary, that's what gets you."

Citazione di: sgnablo il 25 Febbraio 2016, 11:12:28
non laurearti :lkof:
A quello ci sta già pensando il laser, ieri sembrava stesse per rompersi e lì sì che non mi sarei laureato :asdrule:
Si 'u ciucciu 'un vò ma viva, avaca ma frischi...

Ok, sto facendo passi avanti per le due scatole:


#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <string.h>

typedef struct count
{
uint64_t timestamp;
uint16_t channel;
} input;

size_t fsize(FILE* file)
{
if( !file ) { return 0; }

const size_t curr_position = ftell(file);

fseek(file, 0, SEEK_END);
size_t file_size = ftell(file);
fseek(file, curr_position, SEEK_SET);

return file_size;
}

int main(int argc, char const *argv[])
{
FILE *infile1, *infile2;
FILE *outdoubles, *outsingles;

uint64_t ts1_ref, ts2_ref;

uint32_t counts[14];

// Opening input files
infile1 = fopen("timestamps1.txt", "rb");
if(!infile1) return -1;
infile2 = fopen("timestamps2.txt", "rb");
if(!infile2) return -1;

//outdoubles = fopen("coincidences.dat", "w");

// Defining file_sizes so that the last few bits will be discarded in case they're not exactly 10
size_t file_size1 = fsize(infile1) - 40;
file_size1 -= file_size1 % 10;
size_t file_size2 = fsize(infile2) - 40;
file_size2 -= file_size2 % 10;

// Allocating memory to contain the files
input *data1, *data2;

data1 = malloc(sizeof(input)*file_size1);
data2 = malloc(sizeof(input)*file_size2);


// Discarding the 40 bytes headers
fseek(infile1, 40, SEEK_SET);
fseek(infile2, 40, SEEK_SET);

// Copying the files in memory
fread(data1, sizeof(input), file_size1, infile1);
fread(data2, sizeof(input), file_size2, infile2);

while(!data1){
printf("%u, ", data1[i].timestamp);
printf("%u\n", data1[i].channel);
getchar();
}
return 0;
}


L'output però non è rassicurante:

292720139, 7

458752, 0

4487, 35030

2993422341, 0

0, 4519

299525671, 7
Si 'u ciucciu 'un vò ma viva, avaca ma frischi...

Triplo post, chiedo venia :-[

Ma è importante: HO RISOLTO!!!  ;D :tnz: :mki:

Ora ho solo un problema: se uso file grandi (>100MB) va in segfault. Stavo pensando di inserire un buffer e leggere i file poco a poco, ma così potrei perdere delle coincidenze (tra l'ultimo del primo buffer e il primo del buffer successivo).

Idee?

Vi allego il codice:
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <string.h>
#include <stdbool.h>

// Defined a "count" structure. It should contain a uint64_t and a uint16_t,
// but then it would create a 48-bit offset due to the structure padding.
// I hence define just one array of chars (each char is a byte) of the right length
// (10 byte), and then use the following functions to get the actual data (when needed).
typedef struct count{
//uint64_t timestamp;
//uint16_t channel;

#define OFFSET_TS 0
#define OFFSET_CH OFFSET_TS + sizeof(uint64_t)
#define OFFSET_END OFFSET_CH + sizeof(uint16_t)

char data[OFFSET_END];

} input;

size_t fsize(FILE* file){
if( !file ) { return 0; }

const size_t curr_position = ftell(file);

fseek(file, 0, SEEK_END);
size_t file_size = ftell(file);
fseek(file, curr_position, SEEK_SET);

return file_size;
}

// This function sets the timestamp value to the structure.
// Basically it should copy the bits of memory containing "val"
// in the right position of the structure
void setTimestamp(struct count *o, uint64_t val) {
    memcpy(o->data + OFFSET_TS, &val, sizeof(val));
}

// This function sets the channel value to the structure.
// Basically it should copy the bits of memory containing "val"
// in the right position of the structure
void setChannel(struct count *o, uint16_t val) {
    memcpy(o->data + OFFSET_CH, &val, sizeof(val));
}

// This function returns the value of the timestamp written in the structure.
// It gets "val" from the position in "data" containing its allocation.
uint64_t getTimestamp(struct count o){
uint64_t val;
    memcpy(&val, o.data + OFFSET_TS, sizeof(val));
    return val;
}

// This function returns the value of the channel written in the structure.
// It gets "val" from the position in "data" containing its allocation.
uint16_t getChannel(struct count o){
uint16_t val;
    memcpy(&val, o.data + OFFSET_CH, sizeof(val));
    return val;
}

// This function merges and sorts the two arrays of structs  based on their
// (relative) timestamp values.
void *mergeAndSort(struct count *list1, struct count *list2, struct count *dest_list, size_t size1, size_t size2){

if (list2 == NULL)
   memcpy(dest_list, list1, sizeof(input)*size1);

uint64_t j = 0;
uint64_t listIndex = 0;

for(uint64_t i = 0; i < size1 / sizeof(input); i++){
while(getTimestamp(list1[i]) > getTimestamp(list2[j])){
memcpy(dest_list + listIndex, list2 + j, sizeof(input));
listIndex++;
j++;
}
memcpy(dest_list + listIndex, list1 + i, sizeof(input));
listIndex++;
}
}

int main(int argc, char const *argv[])
{

// Initializing the filenames
FILE *infile1, *infile2;
FILE *outdoubles, *outsingles, *outcoinccounts;

// Initializing the reference timestamps for the two files
uint64_t ts1_ref, ts2_ref;

// Initializing the two arrays for, respectively, the singles and the coincidences counts
uint64_t counts[16] = {0};
uint64_t coinc_counts[16][16] = {{0}};

// Initializing the timestamp and channel pairs to be compared
uint64_t timestamp[2];
uint16_t channel[2];

// Opening input files
infile1 = fopen("timestamps1.txt", "rb");
if(!infile1) return -1;
infile2 = fopen("timestamps2.txt", "rb");
if(!infile2) return -1;

// Opening coincidences output file
outdoubles = fopen("coincidences.dat", "wb");

// Defining file_sizes so that the last few bits will be discarded in case they're not exactly 10
size_t file_size1 = fsize(infile1) - 40;
file_size1 -= file_size1 % 10;
size_t file_size2 = fsize(infile2) - 40;
file_size2 -= file_size2 % 10;

// Initializing memory to contain the files
struct count *data1, *data2, *total_array;

// Allocating memory to contain the files
data1 = malloc(file_size1);
data2 = malloc(file_size2);

// Discarding the 40 bytes headers
fseek(infile1, 40, SEEK_SET);
fseek(infile2, 40, SEEK_SET);

// Copying the files in memory
fread(data1, sizeof(input), file_size1 / sizeof(input), infile1);
fread(data2, sizeof(input), file_size2 / sizeof(input), infile2);

// Closing the input files (no longer needed)
fclose(infile1);
fclose(infile2);

// Initializing the variables needed to parse the two arrays
bool GOT_REF = false;
uint64_t ts_old = 0;
uint16_t ch_old = 0;

// Initializing the two reference indexes (needed to discard whatever
// comes before the first counts on channel 8)
uint64_t ref1 = 0, ref2 = 0;

// Parsing the first array: subtracting the reference timestamps
for(int i = 0; i < file_size1 / sizeof(input); i++){

// Start reading the first array when the first counts on channel 8 occur
if(GOT_REF == false){
if(getChannel(data1[i])==7){
GOT_REF = true;
ts1_ref = getTimestamp(data1[i]);
ref1 = i + 1;
}

continue;
}


ts_old = getTimestamp(data1[i]);

setTimestamp(data1 + i, ts_old - ts1_ref);
}

// Parsing the second array: subtracting the reference timestamps and
// adding 8 to the channels.
GOT_REF = false;

for(int i = 0; i < file_size2 / sizeof(input); i++){

// Start reading the first array when the first counts on channel 8 occur
if(GOT_REF == false){
if(getChannel(data2[i])==7){
GOT_REF = true;
ts2_ref = getTimestamp(data2[i]);
ref2 = i + 1;
}
continue;
}

ts_old = getTimestamp(data2[i]);
ch_old = getChannel(data2[i]);

setTimestamp(data2 + i, ts_old - ts2_ref);
setChannel(data2 + i, ch_old + 8);
}

// Allocating memory to contain the entire two files
total_array = malloc(file_size1 + file_size2 - (ref1 + ref2 - 2)*sizeof(input));

// Merge and sort the arrays
mergeAndSort(data1 + ref1, data2 + ref2, total_array, file_size1 - (ref1 - 1)*sizeof(input), file_size2 - (ref2 - 1)*sizeof(input) );

/* *** Debug lines - Add a "/" at the end of this line *** *
for(int i = 0; i < (file_size1 + file_size2) / sizeof(input); i++){
printf("%u, ", getTimestamp(total_array[i]));
printf("%u\n", getChannel(total_array[i]));
getchar();
}
/* *** End of debug lines *** */

// Start finding the coincidences
// Reading the first timestamp-channel couple
timestamp[0] = getTimestamp(total_array[0]);
channel[0] = getChannel(total_array[0]);

// Registering the single count to the right channel
counts[channel[0]]++;


uint64_t timetag_index; // Marker for the following loop

for(int timetag_index = 1; timetag_index < ((file_size1 + file_size2) / sizeof(input)) - (ref1 + ref2 -2); timetag_index++)
{
// Skipping the 7 and 15 channels
if(getChannel(total_array[timetag_index]) == 7 || getChannel(total_array[timetag_index]) == 15){
continue;}

// Getting the data
timestamp[1] = getTimestamp(total_array[timetag_index]);
channel[1] = getChannel(total_array[timetag_index]);

// Incrementing the singles count for the channel
counts[channel[1]]++;

/* *** Debug lines - Uncomment the following *** *
printf("%u, ", timestamp[1]);
printf("%u\n", channel[1]);
if(channel[1]==7||channel[1]==15)
getchar();
/* *** End of debug lines *** */


if(abs(timestamp[1] - timestamp[0]) < 100) // If a coincidence occurs
{
/* *** Debug lines - Uncomment the following *** *
printf("%s %u, %u\n", "Coincidence found! Channels: ", channel[0], channel[1]);
printf("%s %u, ", "Timestamps are: ", timestamp[0]);
printf("%u\n", timestamp[1]);
printf("%s %u\n", "Difference is: ", abs(timestamp[1] - timestamp[0]));
getchar();
/* *** End of debug lines *** */

// Printing coincidence to file
fprintf(outdoubles, "%u,", channel[0]+1);
fprintf(outdoubles, "%u\n", channel[1]+1);

// Incrementing the coincidences count for this coincidence
coinc_counts[channel[0]][channel[1]]++;
}

timestamp[0] = timestamp[1];
channel[0] = channel[1];

}

fclose(outdoubles);

// Opening the singles output file
outsingles = fopen("singles.dat","w");

// Writing counts to file
for(int i = 0; i < 16; i++)
{
if(i == 7 || i == 15) continue;
fprintf(outsingles,"%u\n", counts[i]); // Writing counts to file
}
fclose(outsingles);

// Opening the coincidences count output file
outcoinccounts = fopen("coinc_counts.dat","w");

// Writing counts to file
for(int i = 0; i < 16; i++)
{
for(int j = 0; j < 16; j++)
{
fprintf(outcoinccounts,"%u", coinc_counts[i][j]);
if(j != 15)
fprintf(outcoinccounts, "%s", ", ");
else
fprintf(outcoinccounts,"\n");
}
}

fclose(outcoinccounts);

return 0;
}
Si 'u ciucciu 'un vò ma viva, avaca ma frischi...