major folder reorganisation, R pkg is now epclust/ at first level. Experimental usage...
[epclust.git] / old_C_code / stage1 / src / Util / utils.c
diff --git a/old_C_code/stage1/src/Util/utils.c b/old_C_code/stage1/src/Util/utils.c
new file mode 100644 (file)
index 0000000..91ea075
--- /dev/null
@@ -0,0 +1,138 @@
+#include "Util/utils.h"
+#include <math.h>
+#include <cgds/Vector.h>
+
+void free_work(Work_t* work)
+{
+       free(work->inputFileName);
+       free(work->ranks);
+       free(work);
+}
+
+void free_result(Result_t* result)
+{
+       free(result->medoids_ID);
+       free(result->medoids_ranks);
+       free(result);
+}
+
+char readInt(FILE* stream, int64_t* integer)
+{
+       *integer = 0;
+       char curChar = fgetc(stream);
+       int sign = (curChar == '-' ? -1 : 1);
+       while (curChar < '0' || curChar > '9')
+               curChar = fgetc(stream);
+       ungetc(curChar, stream);
+       while ((curChar = fgetc(stream)) >= '0' && curChar <= '9')
+               *integer = 10 * (*integer) + (int64_t) (curChar - '0');
+       (*integer) *= sign;
+       return curChar;
+}
+
+char readReal(FILE* stream, float* real)
+{
+       int64_t integerPart;
+       char nextChar = readInt(stream, &integerPart);
+       int64_t fractionalPart = 0;
+       int countZeros = 0;
+       if (nextChar == '.')
+       {
+               //need to count zeros
+               while ((nextChar = fgetc(stream)) == '0')
+                       countZeros++;
+               if (nextChar >= '0' && nextChar <= '9')
+               {
+                       ungetc(nextChar, stream);
+                       nextChar = readInt(stream, &fractionalPart);
+               }
+       }
+       int64_t exponent = 0;
+       if (nextChar == 'e' || nextChar == 'E')
+               nextChar = readInt(stream, &exponent);
+       int64_t divisorForFractional = pow(10, floor(log10(fractionalPart > 0 ? fractionalPart : 1))+1);
+       *real = ( (float)integerPart 
+               + (integerPart < 0 ? -1 : 1) * (float)fractionalPart/(divisorForFractional*pow(10,countZeros)) )
+                       * pow(10,exponent);
+       return nextChar;
+}
+
+// convert n-bytes binary integers to uint32_t
+uint32_t bInt_to_uint(Byte* pInteger)
+{
+       uint32_t res;
+       memcpy(&res, pInteger, 4);
+       return res;
+}
+
+// serialize integers
+void write_int(uint32_t x, Byte* buffer)
+{
+       union {
+               uint32_t i;
+               char bytes[4];
+       } u;
+       u.i = x;
+       for (size_t i = 0; i < 4; i++)
+               buffer[i] = u.bytes[i];
+}
+
+//WARNING: assuming float is 32bits...
+// convert 4-bytes binary float to float
+float bReal_to_float(Byte* pFloat)
+{
+       float res;
+       memcpy(&res, pFloat, 4);
+       return res;
+}
+
+//WARNING: assuming float is 32bits...
+// serialize double with a NON-portable bytes order
+void write_real(float x, Byte* buffer)
+{
+       union {
+               float d;
+               char bytes[4];
+       } u;
+       u.d = x;
+       for (size_t i = 0; i < 4; i++)
+               buffer[i] = u.bytes[i];
+}
+
+// Expected size of a Work message in bytes:
+uint32_t get_packedWork_length(uint32_t nbSeriesInChunk)
+{
+       return NCHAR_FNAME + 4 + 4*nbSeriesInChunk + 4 + 4 + 4;
+}
+
+// Expected size of a Result message in bytes: (uint32_t is on 4 bytes)
+uint32_t get_packedResult_length(uint32_t nbClusters)
+{
+       return 4 + 4 * nbClusters + 4 * nbClusters;
+}
+
+// get metadata: nbSeries
+uint32_t get_nbSeries(const char* ifileName)
+{
+       FILE* ifile = fopen(ifileName, "rb");
+       fseek(ifile, 0, SEEK_SET);
+       Byte binaryInt[4];
+       size_t lengthRead = fread(binaryInt, 4, 1, ifile);
+       if (lengthRead != 1)
+               fprintf(stderr,"Warning: getting nbSeries from truncated binary file.\n");
+       fclose(ifile);
+       return bInt_to_uint(binaryInt);
+}
+
+// get metadata: tsLength
+uint32_t get_tsLength(const char* ifileName)
+{
+       FILE* ifile = fopen(ifileName, "rb");
+       fseek(ifile, 4, SEEK_SET);
+       Byte binaryInt[4];
+       size_t lengthRead = fread(binaryInt, 4, 1, ifile);
+       if (lengthRead != 1)
+               fprintf(stderr,"Warning: getting tsLength from truncated binary file.\n");
+       fclose(ifile);
+       return bInt_to_uint(binaryInt);
+}