AiLibrary  v1.3.0
A single-header C++ Library from Ailurus Studio
ai.hh
Go to the documentation of this file.
1 #if !defined(AILIBRARY_HH)
2 #define AILIBRARY_HH
3 
15 
19 #define INLINE inline
20 
21 // /// \brief If defined, functions using dirent.h will be included
22 // /// \details If defined, functions using dirent.h (POSIX) will be included.
23 // /// Uncomment the line or pass the defined value at compile time if you want
24 // /// this behavior. Windows users may need to specify the location of the
25 // /// header below
26 #define AI_DIRENT_SUPPORT
27 
28 // /// \brief If defined, functions requiring GCC v5+ will be included
29 // /// \details If defined, functions requiring GCC v5+ will be included.
30 // /// Uncomment the line or pass the defined value at compile time if you want
31 // /// this behavior.
32 #define AI_GCC5_SUPPORT
33 
34 // /// \brief If defined, functions requiring UNIX shell will be included
35 // /// \details If defined, functions requiring UNIX shell will be included.
36 // /// Uncomment the line or pass the defined value at compile time if you want
37 // /// this behavior.
38 #define AI_SHELL_SUPPORT
39 
40 // /// \brief If defined, declarations of not yet implemented functions will be
41 // /// accessible
42 // /// \details If defined, declarations of not yet implemented functions will
43 // /// be accessible. Uncomment the line or pass the defined value at compile
44 // /// time if you want this behavior
45 // #define AI_FUTURE
46 
47 #include <array>
48 #include <cmath>
49 #include <chrono>
50 #include <limits>
51 #include <memory>
52 #include <random>
53 #include <string>
54 #include <vector>
55 #include <cstdlib>
56 #include <iomanip>
57 #include <fstream>
58 #include <sstream>
59 #include <iostream>
60 #include <algorithm>
61 #include <stdexcept>
62 #include <sys/stat.h>
63 
64 #if defined(AI_DIRENT_SUPPORT)
65  #include <dirent.h>
69  // #include "include/dirent/dirent.h"
70 #endif
71 
76 
80 #define STRINGIFY(x) #x
81 
85 #define TO_STRING(x) STRINGIFY(x)
86 
89 #define PRINT_LINE() std::cout << "Line #" << __LINE__ << std::endl
90 
92 
100 namespace ai{
106 
113  return std::string("1.3.0");
114  }
115 
117 
123 
131  template<typename T>
132  INLINE std::string string(const T value){
133  std::ostringstream stream;
134 
135  stream << value;
136 
137  return stream.str();
138  }
139 
146  INLINE bool hasPrefix(const std::string &text, const std::string &prefix){
147  return text.size() >= prefix.size()
148  && 0 == text.compare(0, prefix.size(), prefix);
149  }
150 
157  INLINE bool hasSuffix(const std::string &text, const std::string &suffix){
158  return text.size() >= suffix.size()
159  && 0 == text.compare(
160  text.size() - suffix.size(),
161  suffix.size(),
162  suffix
163  );
164  }
165 
174  const std::string &text,
175  const std::string &substring
176  ){
177  return std::string::npos != text.find(substring);
178  }
179 
192  std::string text,
193  const std::string &substring,
194  const std::string &replacement
195  ){
196  std::size_t position = text.find(substring);
197  std::size_t substringSize = substring.size();
198  std::size_t replacementSize = replacement.size();
199 
200  while(std::string::npos != position){
201  text.replace(position, substringSize, replacement);
202  position = text.find(substring, position + replacementSize);
203  }
204  return text;
205  }
206 
217  std::string &text,
218  const std::string &substring,
219  const std::string &replacement
220  ){
221  std::size_t position = text.find(substring);
222  std::size_t substringSize = substring.size();
223  std::size_t replacementSize = replacement.size();
224 
225  while(std::string::npos != position){
226  text.replace(position, substringSize, replacement);
227  position = text.find(substring, position + replacementSize);
228  }
229  }
230 
237  INLINE bool equal(const char *charString, const std::string string1){
238  const std::string string2(charString);
239 
240  return string1 == string2;
241  }
242 
251  std::transform(input.begin(), input.end(), input.begin(), ::toupper);
252 
253  return input;
254  }
255 
264  std::transform(input.begin(), input.end(), input.begin(), ::tolower);
265 
266  return input;
267  }
268 
281  template<typename T>
283  const T value,
284  const std::size_t symbolsBeforePoint,
285  const char symbolToPrepend = '0'
286  ){
287  std::string token = ai::string(value);
288 
289  const int counter = symbolsBeforePoint
290  - (ai::string((int) value)).size();
291 
292  for(int i = 0; i < counter; ++i){
293  token = ai::string(symbolToPrepend) + token;
294  }
295 
296  return token;
297  }
298 
300 
306 
314  INLINE std::size_t counter(const std::size_t value = 0){
315  static std::size_t count = 0;
316 
317  ++count;
318 
319  if(0 != value){
320  count = value;
321  }
322 
323  return count;
324  }
325 
334  INLINE std::string marker(const std::size_t value = 0){
335  static std::size_t count = 0;
336 
337  ++count;
338 
339  if(0 != value){
340  count = value;
341  }
342 
343  return "Marker #" + ai::string(count);
344  }
345 
351  INLINE void printMarker(const std::size_t value = 0){
352  std::cout << marker(value) << std::endl;
353  }
354 
356 
362 
365  static const double e = 2.71828182845904523536;
366 
369  static const double pi = 3.14159265358979323846;
370 
378  template<typename T>
379  INLINE T sign(const T value){
380  if(0 == value){
381  return (T) 0;
382  }
383 
384  return copysign(1, value);
385  }
386 
394  template<typename T>
395  INLINE T min(const T a, const T b){
396  if(a > b){
397  return b;
398  }
399 
400  return a;
401  }
402 
410  template<typename T>
411  INLINE T max(const T a, const T b){
412  if(a < b){
413  return b;
414  }
415 
416  return a;
417  }
418 
427  template<typename T>
428  INLINE T min(const std::vector<T> &input){
429  T minimum = input[0];
430 
431  for(std::size_t i = 1; i < input.size(); ++i){
432  minimum = ai::min(minimum, input[i]);
433  }
434 
435  return minimum;
436  }
437 
446  template<typename T>
447  INLINE T max(const std::vector<T> &input){
448  T maximum = input[0];
449 
450  for(std::size_t i = 1; i < input.size(); ++i){
451  maximum = ai::max(maximum, input[i]);
452  }
453 
454  return maximum;
455  }
456 
465  template<typename T>
466  INLINE T min(const std::vector< std::vector<T> > &input){
467  T minimum = input[0][0];
468 
469  for(std::size_t i = 0; i < input.size(); ++i){
470  for(std::size_t j = 0; j < input[0].size(); ++j){
471  minimum = ai::min(minimum, input[i][j]);
472  }
473  }
474 
475  return minimum;
476  }
477 
486  template<typename T>
487  INLINE T max(const std::vector< std::vector<T> > &input){
488  T maximum = input[0][0];
489 
490  for(std::size_t i = 0; i < input.size(); ++i){
491  for(std::size_t j = 0; j < input[0].size(); ++j){
492  maximum = ai::max(maximum, input[i][j]);
493  }
494  }
495 
496  return maximum;
497  }
498 
506  template<typename T>
507  INLINE bool isSquare(const T value){
508  if(0 >= value){
509  return false;
510  }
511 
512  T root = (T) round(sqrt(value));
513 
514  return value == root * root;
515  }
516 
524  template<typename T>
525  INLINE bool isSquare(const std::vector< std::vector<T> > &matrix){
526  return 0 < matrix.size() && matrix.size() == matrix[0].size();
527  }
528 
541  template<typename T>
543  std::vector<T> &vector,
544  const std::size_t length,
545  const T min = std::numeric_limits<T>::min(),
546  const T max = std::numeric_limits<T>::max()
547  ){
548  std::uniform_real_distribution<T> distribution(min, max);
549  std::random_device device;
550 
551  double currentTime =
552  (double) (
553  std::chrono::high_resolution_clock::now()
554  ).time_since_epoch().count();
555 
556  srand(device() * currentTime);
557 
558  vector.resize(length);
559 
560  std::generate(
561  vector.begin(),
562  vector.end(),
563  [&device, &distribution](){
564  return distribution(device);
565  }
566  );
567  }
568 
583  template<typename T>
585  std::vector< std::vector<T> > &matrix,
586  const std::size_t xSize,
587  const std::size_t ySize,
588  const T min = std::numeric_limits<T>::min(),
589  const T max = std::numeric_limits<T>::max()
590  ){
591  matrix.resize(xSize);
592 
593  for(size_t i = 0; i < xSize; ++i){
594  matrix[i].resize(ySize);
595 
596  std::vector<T> row;
597 
598  ai::generateRandomVector(row, ySize, min, max);
599 
600  matrix[i] = row;
601  }
602  }
603 
616  template<typename T>
618  std::vector< std::vector<T> > &matrix,
619  const std::size_t size,
620  const T min = std::numeric_limits<T>::min(),
621  const T max = std::numeric_limits<T>::max()
622  ){
623  ai::generateRandomMatrix(matrix, size, size, min, max);
624  }
625 
636  template<typename T>
638  std::vector< std::vector<T> > &matrix,
639  const bool rotateClockwise = false
640  ){
641  std::size_t length = matrix.size();
642 
643  if(rotateClockwise){
644  for(std::size_t i = 0; i < length / 2; ++i){
645  for(std::size_t j = i; j < length - i - 1; ++j){
646  T savedValue = matrix[i][j];
647 
648  matrix[i][j] = matrix[length - 1 - j][i];
649  matrix[length - 1 - j][i] =
650  matrix[length - 1 - i][length - 1 - j];
651  matrix[length - 1 - i][length - 1 - j] =
652  matrix[j][length - 1 - i];
653  matrix[j][length - 1 - i] = savedValue;
654  }
655  }
656  }else{
657  for(std::size_t i = 0; i < length / 2; ++i){
658  for(std::size_t j = i; j < length - i - 1; ++j){
659  T savedValue = matrix[i][j];
660 
661  matrix[i][j] = matrix[j][length - 1 - i];
662  matrix[j][length - 1 - i] =
663  matrix[length - 1 - i][length - 1 - j];
664  matrix[length - 1 - i][length - 1 - j] =
665  matrix[length - 1 - j][i];
666  matrix[length - 1 - j][i] = savedValue;
667  }
668  }
669  }
670  }
671 
673  template<typename T>
675  std::vector< std::vector<T> > matrix,
676  std::vector< std::vector<T> > &inverse
677  ){
678  if(!isSquare(matrix)){
679  throw std::runtime_error(
680  std::string("Exception while inversing: ")
681  + std::string("matrix should be square")
682  );
683  }
684 
685  const std::size_t length = matrix.size();
686 
687  inverse.clear();
688  inverse.resize(length);
689 
690  for(std::size_t i = 0; i < length; ++i){
691  inverse[i].resize(length);
692 
693  inverse[i][i] = (T) 1.;
694  }
695 
696  T ratio = 0;
697 
698  for(std::size_t i = 0; i < length; ++i){
699  for(std::size_t j = 0; j < length; ++j){
700  if(i != j){
701  ratio = matrix[j][i] / matrix[i][i];
702 
703  for(std::size_t k = 0; k < length; ++k){
704  matrix[j][k] -= ratio * matrix[i][k];
705  inverse[j][k] -= ratio * inverse[i][k];
706  }
707  }
708  }
709  }
710  for(std::size_t i = 0; i < length; ++i){
711  for(std::size_t j = 0; j < length; ++j){
712  inverse[i][j] /= matrix[i][i];
713  }
714  }
715  }
716 
718  template<typename T>
720  std::vector< std::vector<T> > &matrix
721  ){
722  ai::inverseMatrix(matrix, matrix);
723  }
724 
734  template<typename T>
736  std::vector< std::vector<T> > &matrix,
737  std::vector<T> &vector
738  ){
739  for(std::size_t i = 0; i < matrix.size(); ++i){
740  for(std::size_t j = 0; j < matrix[i].size(); ++j){
741  vector.push_back(matrix[i][j]);
742  }
743  }
744  }
745 
756  template<typename T>
758  std::vector<T> &vector,
759  std::vector< std::vector<T> > &matrix
760  ){
761  if(!isSquare(vector.size())){
762  throw std::runtime_error(
763  ai::string("Exception while converting vector into the ")
764  + ai::string("square matrix: vector size should be square")
765  );
766  }
767 
768  std::size_t size = (std::size_t) round(sqrt(vector.size()));
769 
770  for(std::size_t i = 0; i < size; ++i){
771  std::vector<T> row;
772 
773  for(std::size_t j = 0; j < size; ++j){
774  row.push_back(vector[i * size + j]);
775  }
776 
777  matrix.push_back(row);
778  }
779  }
780 
795  template<typename T>
797  std::vector< std::vector<T> > &matrix,
798  std::vector<T> &source,
799  const bool moveToTheRight = true
800  ){
801  if(1 > source.size()){
802  throw std::runtime_error(
803  ai::string("Exception while creating a circulant: ")
804  + ai::string("size of the source should be at least 1.")
805  );
806  }
807 
808  std::size_t length = source.size();
809 
810  std::size_t displacement = 0;
811 
812  matrix.clear();
813  matrix.resize(length);
814 
815  if(moveToTheRight){
816  for(std::size_t i = 0; i < length; ++i){
817  matrix[i].resize(length);
818 
819  std::size_t k = displacement;
820 
821  for(std::size_t j = 0; j < length - displacement; ++j){
822  matrix[i][k] = source[j];
823 
824  ++k;
825  }
826 
827  k = 0;
828 
829  for(std::size_t j = length - displacement; j < length; ++j){
830  matrix[i][k] = source[j];
831 
832  ++k;
833  }
834 
835  ++displacement;
836  }
837  }else{
838  for(std::size_t i = 0; i < length; ++i){
839  matrix[i].resize(length);
840 
841  std::size_t k = 0;
842 
843  for(std::size_t j = displacement; j < length; ++j){
844  matrix[i][k] = source[j];
845 
846  ++k;
847  }
848 
849  for(std::size_t j = 0; j < displacement; ++j){
850  matrix[i][k] = source[j];
851 
852  ++k;
853  }
854 
855  ++displacement;
856  }
857  }
858  }
859 
871  template<typename T>
873  const std::vector< std::vector<T> > &left,
874  const std::vector< std::vector<T> > &right,
875  std::vector< std::vector<T> > &result
876  ){
877  if(
878  1 > left.size()
879  || 1 > right.size()
880  || left[0].size() != right.size()
881  ){
882  throw std::runtime_error(
883  "Exception while multiplying: check the sizes of the input."
884  );
885  }
886 
887  std::size_t vLength = left.size();
888  std::size_t hLength = right[0].size();
889  std::size_t fLength = left[0].size();
890 
891  result.resize(vLength);
892 
893  for(std::size_t i = 0; i < vLength; ++i){
894  result[i].resize(hLength);
895 
896  for(std::size_t j = 0; j < hLength; ++j){
897  result[i][j] = (T) 0.;
898  }
899  for(std::size_t k = 0; k < fLength; ++k){
900  for(std::size_t j = 0; j < hLength; ++j){
901  result[i][j] += left[i][k] * right[k][j];
902  }
903  }
904  }
905  };
906 
917  template<typename T>
919  const std::vector< std::vector<T> > &left,
920  const std::vector<T> &right,
921  std::vector<T> &result
922  ){
923  if(1 > left.size() || left[0].size() != right.size()){
924  throw std::runtime_error(
925  "Exception while multiplying: check the sizes of the input."
926  );
927  }
928 
929  std::size_t vLength = left.size();
930 
931  int hLength = (int) right.size();
932  int j = 0;
933 
934  result.resize(vLength);
935 
936  for(int i = 0; i < vLength; ++i){
937  j = 0;
938  result[i] = (T) 0.;
939 
940  for(; j <= hLength - 4; j += 4){
941  result[i] += left[i][j] * right[j]
942  + left[i][j + 1] * right[j + 1]
943  + left[i][j + 2] * right[j + 2]
944  + left[i][j + 3] * right[j + 3];
945  }
946  for(; j < hLength; ++j){
947  result[i] += left[i][j] * right[j];
948  }
949  }
950  }
951 
962  template<typename T>
964  const std::vector<T> &left,
965  const std::vector<T> &right,
966  T &result
967  ){
968  if(left.size() != right.size()){
969  throw std::runtime_error(
970  "Exception while multiplying: check the sizes of the input."
971  );
972  }
973 
974  int length = (int) left.size();
975  int i = 0;
976 
977  result = (T) 0.;
978 
979  for(; i <= length - 4; i += 4){
980  result += left[i] * right[i]
981  + left[i + 1] * right[i + 1]
982  + left[i + 2] * right[i + 2]
983  + left[i + 3] * right[i + 3];
984  }
985  for(; i < length; ++i){
986  result += left[i] * right[i];
987  }
988  }
989 
1002  template<typename T>
1004  const std::vector< std::vector<T> > &left,
1005  const std::vector< std::vector<T> > &right,
1006  std::vector< std::vector<T> > &result
1007  ){
1008  if(
1009  1 > left.size()
1010  || 1 > right.size()
1011  || left.size() != right.size()
1012  || left[0].size() != right[0].size()
1013  ){
1014  throw std::runtime_error(
1015  "Exception while multiplying: check the sizes of the input."
1016  );
1017  }
1018 
1019  std::size_t vLength = left.size();
1020  std::size_t hLength = left[0].size();
1021 
1022  result.resize(vLength);
1023 
1024  for(std::size_t i = 0; i < vLength; ++i){
1025  result[i].resize(hLength);
1026 
1027  for(std::size_t j = 0; j < hLength; ++j){
1028  result[i][j] = left[i][j] * right[i][j];
1029  }
1030  }
1031  }
1032 
1044  template<typename T>
1046  const std::vector<T> &left,
1047  const std::vector<T> &right,
1048  std::vector<T> &result
1049  ){
1050  if(left.size() != right.size()){
1051  throw std::runtime_error(
1052  "Exception while multiplying: check the sizes of the input."
1053  );
1054  }
1055 
1056  int length = (int) left.size();
1057 
1058  result.resize(length);
1059 
1060  for(std::size_t i = 0; i < length; ++i){
1061  result[i] = left[i] * right[i];
1062  }
1063  }
1064 
1067  template<typename T>
1069  const std::vector< std::vector<T> > &left,
1070  const std::vector< std::vector<T> > &right,
1071  std::vector< std::vector<T> > &result
1072  ){
1073  if(
1074  left.size() != right.size()
1075  || 2 != left[0].size()
1076  || 2 != right[0].size()
1077  ){
1078  throw std::runtime_error(
1079  "Exception while multiplying: check the sizes of the input."
1080  );
1081  }
1082 
1083  const std::size_t length = left.size();
1084 
1085  result.resize(length);
1086 
1087  for(std::size_t i = 0; i < length; ++i){
1088  result[i].resize(2);
1089 
1090  result[i][0] = left[i][0] * right[i][0]
1091  - left[i][1] * right[i][1];
1092  result[i][1] = left[i][0] * right[i][1]
1093  + left[i][1] * right[i][0];
1094  }
1095  }
1096 
1099  template<typename T>
1100  INLINE std::string complexIntoString(const std::vector<T> complexValue){
1101  return ai::string(complexValue[0]) + ai::string(" + i")
1102  + ai::string(complexValue[1]);
1103  }
1104 
1107  template<typename T>
1108  INLINE void conjugate(std::vector< std::vector<T> > &complexVector){
1109  const std::size_t length = complexVector.size();
1110 
1111  for(std::size_t i = 0; i < length; ++i){
1112  complexVector[i][1] = -complexVector[i][1];
1113  }
1114  }
1115 
1118  template<typename T>
1119  INLINE void fft(std::vector< std::vector<T> > &complexVector){
1120  const std::size_t length = complexVector.size();
1121 
1122  if(2 > length || !(length & (length - 1)) == 0){
1123  throw std::runtime_error(
1124  std::string("Exception while calculating FFT: ")
1125  + std::string("vector length must be a power of two.")
1126  );
1127  }
1128 
1129  std::size_t j = 0;
1130  std::size_t k = length;
1131  std::size_t n = 0;
1132 
1133  const double doubleTypeLength = (double) k;
1134 
1135  double thetaT = ai::pi / doubleTypeLength;
1136  double swap0 = 0.;
1137  double swap1 = 0.;
1138  double T0 = 1.;
1139  double T1 = 0.;
1140  double phiT0 = cos(thetaT);
1141  double phiT1 = -sin(thetaT);
1142 
1143  while(1 < k){
1144  n = k;
1145  T0 = 1.;
1146  T1 = 0.;
1147  swap0 = phiT0;
1148  swap1 = phiT1;
1149  phiT0 = swap0 * swap0 - swap1 * swap1;
1150  phiT1 = 2. * swap0 * swap1;
1151  k >>= 1;
1152 
1153  for(std::size_t l = 0; l < k; ++l){
1154  for(std::size_t i = l; i < length; i += n){
1155  j = i + k;
1156  swap0 = complexVector[i][0] - complexVector[j][0];
1157  swap1 = complexVector[i][1] - complexVector[j][1];
1158  complexVector[i][0] += complexVector[j][0];
1159  complexVector[i][1] += complexVector[j][1];
1160  complexVector[j][0] = swap0 * T0 - swap1 * T1;
1161  complexVector[j][1] = swap0 * T1 + swap1 * T0;
1162  }
1163 
1164  swap0 = T0;
1165  T0 = swap0 * phiT0 - T1 * phiT1;
1166  T1 = swap0 * phiT1 + T1 * phiT0;
1167  }
1168  }
1169 
1170  std::size_t m = (std::size_t) log2(doubleTypeLength);
1171 
1172  for(std::size_t i = 0; i < length; ++i){
1173  j = i;
1174  j = (((j & 0xaaaaaaaa) >> 1) | ((j & 0x55555555) << 1));
1175  j = (((j & 0xcccccccc) >> 2) | ((j & 0x33333333) << 2));
1176  j = (((j & 0xf0f0f0f0) >> 4) | ((j & 0x0f0f0f0f) << 4));
1177  j = (((j & 0xff00ff00) >> 8) | ((j & 0x00ff00ff) << 8));
1178  j = ((j >> 16) | (j << 16)) >> (32 - m);
1179 
1180  if(j > i){
1181  swap0 = complexVector[i][0];
1182  swap1 = complexVector[i][1];
1183  complexVector[i][0] = complexVector[j][0];
1184  complexVector[i][1] = complexVector[j][1];
1185  complexVector[j][0] = swap0;
1186  complexVector[j][1] = swap1;
1187  }
1188  }
1189  }
1190 
1193  template<typename T>
1194  INLINE void ifft(std::vector< std::vector<T> > &complexVector){
1195  const std::size_t length = complexVector.size();
1196 
1197  const double doubleTypeLength = (double) length;
1198 
1199  conjugate(complexVector);
1200  fft(complexVector);
1201  conjugate(complexVector);
1202 
1203  for(std::size_t i = 0; i < length; ++i){
1204  complexVector[i][0] /= doubleTypeLength;
1205  complexVector[i][1] /= doubleTypeLength;
1206  }
1207  }
1208 
1210 
1216 
1222  INLINE std::chrono::high_resolution_clock::time_point time(){
1223  return std::chrono::high_resolution_clock::now();
1224  }
1225 
1231  INLINE std::chrono::system_clock::time_point systemTime(){
1232  return std::chrono::system_clock::now();
1233  }
1234 
1251  const std::chrono::high_resolution_clock::time_point start,
1252  const std::chrono::high_resolution_clock::time_point finish,
1253  const std::string scale = std::string("ms")
1254  ){
1255  if(std::string("h") == scale){
1256  return (double) std::chrono::duration_cast
1257  <std::chrono::hours> (finish - start).count();
1258  }
1259 
1260  if(std::string("m") == scale){
1261  return (double) std::chrono::duration_cast
1262  <std::chrono::minutes> (finish - start).count();
1263  }
1264 
1265  if(std::string("s") == scale){
1266  return (double) std::chrono::duration_cast
1267  <std::chrono::seconds> (finish - start).count();
1268  }
1269 
1270  if(std::string("us") == scale){
1271  return (double) std::chrono::duration_cast
1272  <std::chrono::microseconds> (finish - start).count();
1273  }
1274 
1275  if(std::string("ns") == scale){
1276  return (double) std::chrono::duration_cast
1277  <std::chrono::nanoseconds> (finish - start).count();
1278  }
1279 
1280  return (double) std::chrono::duration_cast
1281  <std::chrono::milliseconds> (finish - start).count();
1282  }
1283 
1286  const std::chrono::high_resolution_clock::time_point start,
1287  const std::string scale = std::string("ms")
1288  ){
1289  return ai::duration(start, ai::time(), scale);
1290  }
1291 
1294  const std::chrono::high_resolution_clock::time_point start,
1295  const std::chrono::high_resolution_clock::time_point finish,
1296  const std::string scale = std::string("ms"),
1297  const std::size_t count = 0
1298  ){
1299  std::cout << "Timer #" << counter(count) << ": "
1300  << ai::duration(start, finish, scale) << scale << std::endl;
1301  }
1302 
1305  const std::chrono::high_resolution_clock::time_point start,
1306  const std::string scale = std::string("ms"),
1307  const std::size_t count = 0
1308  ){
1309  std::chrono::high_resolution_clock::time_point finish = ai::time();
1310 
1311  ai::printDuration(start, finish, scale, count);
1312  }
1313 
1314  #if defined(AI_GCC5_SUPPORT)
1327  std::chrono::system_clock::time_point timePoint =
1328  std::chrono::system_clock::now()
1329  ){
1330  std::time_t date = std::chrono::system_clock::to_time_t(timePoint);
1331 
1332  std::ostringstream stream;
1333 
1334  stream << std::put_time(std::localtime(&date), "%F %T");
1335 
1336  return stream.str();
1337  }
1338 
1349  std::chrono::system_clock::time_point timePoint =
1350  std::chrono::system_clock::now()
1351  ){
1352  std::time_t date = std::chrono::system_clock::to_time_t(timePoint);
1353 
1354  std::ostringstream stream;
1355 
1356  stream << std::put_time(std::localtime(&date), "%F");
1357 
1358  return stream.str();
1359  }
1360 
1371  std::chrono::system_clock::time_point timePoint =
1372  std::chrono::system_clock::now()
1373  ){
1374  std::time_t date = std::chrono::system_clock::to_time_t(timePoint);
1375 
1376  std::ostringstream stream;
1377 
1378  stream << std::put_time(std::localtime(&date), "%T");
1379 
1380  return stream.str();
1381  }
1382 
1383  #endif
1384 
1386 
1392 
1395  const char *input,
1396  const std::string name
1397  ){
1398  std::string parameter(input);
1399 
1400  if(hasPrefix(parameter, name)){
1401  parameter = parameter.substr(name.size());
1402  return parameter;
1403  }
1404 
1405  return NULL;
1406  }
1407 
1410  template<typename T>
1412  T &value,
1413  const T parameter,
1414  const std::vector< std::vector<T> > intervals
1415  ){
1416  for(std::size_t i = 0; i < intervals.size(); ++i){
1417  if(intervals[i][0] <= parameter && parameter <= intervals[i][1]){
1418  value = intervals[i][2];
1419 
1420  return;
1421  }
1422  }
1423  }
1424 
1427  template<typename T>
1429  T &firstValue,
1430  T &secondValue,
1431  const T parameter,
1432  const std::vector< std::vector<T> > intervals
1433  ){
1434  for(std::size_t i = 0; i < intervals.size(); ++i){
1435  if(intervals[i][0] <= parameter && parameter <= intervals[i][1]){
1436  firstValue = intervals[i][1];
1437  secondValue = intervals[i][2];
1438 
1439  return;
1440  }
1441  }
1442  }
1443 
1446  const char *input,
1447  const std::string name,
1448  bool &value
1449  ){
1450  if(name == std::string(input)){
1451  value = true;
1452 
1453  return true;
1454  }
1455 
1456  return false;
1457  }
1458 
1461  const char *input,
1462  const std::string name,
1463  char &value
1464  ){
1465  std::string parameter = std::string(input);
1466 
1467  if(ai::hasPrefix(parameter, name)){
1468  parameter = parameter.substr(name.size());
1469 
1470  if(std::string() != parameter){
1471  value = (char) parameter[0];
1472  }else{
1473  value = ' ';
1474  }
1475 
1476  return true;
1477  }
1478 
1479  return false;
1480  }
1481 
1484  const char *input,
1485  const std::string name,
1486  std::string &value
1487  ){
1488  std::string parameter = std::string(input);
1489 
1490  if(ai::hasPrefix(parameter, name)){
1491  value = parameter.substr(name.size());
1492 
1493  return true;
1494  }
1495 
1496  return false;
1497  }
1498 
1501  template<typename T>
1503  const char *input,
1504  const std::string name,
1505  T &value
1506  ){
1507  std::string parameter = std::string(input);
1508 
1509  if(ai::hasPrefix(parameter, name)){
1510  parameter = parameter.substr(name.size());
1511 
1512  if(std::istringstream(parameter) >> value){
1513  return true;
1514  }
1515  }
1516 
1517  return false;
1518  }
1519 
1522  const char *input,
1523  const std::string name,
1524  double &value
1525  ){
1526  std::string parameter = std::string(input);
1527 
1528  if(ai::hasPrefix(parameter, name)){
1529  parameter = parameter.substr(name.size());
1530  value = std::abs(strtod(parameter.c_str(), nullptr));
1531 
1532  return true;
1533  }
1534 
1535  return false;
1536  }
1537 
1540  template<typename T>
1542  const char *input,
1543  const std::string parameter,
1544  T &value,
1545  const T supposed
1546  ){
1547  if(ai::equal(input, parameter)){
1548  value = supposed;
1549 
1550  return true;
1551  }
1552 
1553  return false;
1554  }
1555 
1557 
1563 
1566  std::cout <<"\033[2J" << "\033[H";
1567  }
1568 
1570  INLINE void setLocale(const std::string locale){
1571  if(std::string("en") == ai::toLowerCase(locale)){
1572  std::locale::global(std::locale("en_US.utf8"));
1573  }else{
1574  std::locale::global(
1575  std::locale(
1576  (
1577  ai::toLowerCase(locale) + ai::string("_")
1578  + ai::toUpperCase(locale) + ai::string(".utf8")
1579  ).c_str()
1580  )
1581  );
1582  }
1583  }
1584 
1594  double progress,
1595  const int screenWidth = 80
1596  ){
1597  if(1 < progress){
1598  progress = 1;
1599  }
1600 
1601  if(0.01 > progress){
1602  progress = 0;
1603  }
1604 
1605  if(20 > screenWidth){
1606  throw std::runtime_error(
1607  ai::string("Screen width should be at least 20 (not ")
1608  + ai::string(screenWidth)
1609  + ai::string(")")
1610  );
1611  }
1612 
1613  const std::size_t barWidth = screenWidth - 7;
1614 
1615  int width = progress * barWidth;
1616 
1617  std::cout << std::fixed;
1618  std::cout.precision(1);
1619  std::cout.flush();
1620 
1621  std::cout << "\r" << std::string(width, '=')
1622  << std::string(barWidth - width, '-')
1623  << " " << progress * 100. << "%";
1624  }
1625 
1637  const std::string line,
1638  const int screenWidth = 80
1639  ){
1640  if(20 > screenWidth){
1641  throw std::runtime_error(
1642  ai::string("Screen width should be at least 20 (not ")
1643  + ai::string(screenWidth)
1644  + ai::string(")")
1645  );
1646  }
1647 
1648  std::cout << "\r" << std::setw(screenWidth) << std::left << line
1649  << std::endl;
1650  }
1651 
1653 
1659 
1663  template<typename T>
1665  const std::string filename,
1666  const char separator,
1667  std::vector< std::vector<T> > &matrix
1668  ){
1669  std::ifstream input(filename);
1670 
1671  if(!input.good()){
1672  throw std::runtime_error(
1673  ai::string("Exception while parsing the file into a matrix: ")
1674  + filename
1675  );
1676  }
1677 
1678  std::string token;
1679 
1680  T value;
1681 
1682  for(std::string line; std::getline(input, line);){
1683  if('#' == line[0]){
1684  continue;
1685  }
1686 
1687  std::istringstream stream(line);
1688 
1689  std::vector<T> row;
1690 
1691  while(std::getline(stream, token, separator)){
1692  if(std::istringstream(token) >> value){
1693  row.push_back(value);
1694  }
1695  }
1696 
1697  matrix.push_back(row);
1698  }
1699 
1700  input.close();
1701  }
1702 
1706  template<typename T>
1708  const std::string filename,
1709  const char separator,
1710  std::vector<T> &vector
1711  ){
1712  std::ifstream input(filename);
1713 
1714  if(!input.good()){
1715  throw std::runtime_error(
1716  ai::string("Exception while parsing the file into a vector: ")
1717  + filename
1718  );
1719  }
1720 
1721  std::string token;
1722 
1723  T value;
1724 
1725  if('\n' == separator){
1726  for(std::string line; std::getline(input, line);){
1727  if('#' == line[0]){
1728  continue;
1729  }
1730 
1731  if(std::istringstream(line) >> value){
1732  vector.push_back(value);
1733  }
1734  }
1735  }else{
1736  std::string line;
1737 
1738  std::getline(input, line);
1739 
1740  std::istringstream stream(line);
1741 
1742  while(std::getline(stream, token, separator)){
1743  if(std::istringstream(token) >> value){
1744  vector.push_back(value);
1745  }
1746  }
1747  }
1748 
1749  input.close();
1750  }
1751 
1755  const std::string filename,
1756  std::string &content
1757  ){
1758  std::ifstream input(filename);
1759 
1760  if(!input.good()){
1761  throw std::runtime_error(
1762  ai::string("Exception while parsing the file into a string: ")
1763  + filename
1764  );
1765  }
1766 
1767  std::ostringstream stream;
1768  stream << input.rdbuf();
1769  content = stream.str();
1770 
1771  input.close();
1772  }
1773 
1776  template<typename T>
1778  const std::string filename,
1779  const char separator,
1780  std::vector< std::vector<T> > &matrix
1781  ){
1782  std::vector< std::vector<T> > matrixToAdd;
1783 
1784  ai::parseFileInMatrix(filename, separator, matrixToAdd);
1785 
1786  for(std::size_t i = 0; i < matrix.size(); ++i){
1787  std::transform(
1788  matrix[i].begin(),
1789  matrix[i].end(),
1790  matrixToAdd[i].begin(),
1791  matrix[i].begin(),
1792  std::plus<T>()
1793  );
1794  }
1795  }
1796 
1799  template<typename T>
1801  const std::string filename,
1802  const char separator,
1803  std::vector<T> &vector,
1804  const bool checkForNaN = false
1805  ){
1806  std::vector<T> vectorToAdd;
1807 
1808  ai::parseFileInVector(filename, separator, vectorToAdd);
1809 
1810  std::transform(
1811  vector.begin(),
1812  vector.end(),
1813  vectorToAdd.begin(),
1814  vector.begin(),
1815  std::plus<T>()
1816  );
1817  }
1818 
1820 
1826 
1829  template<typename T>
1831  const std::vector<std::vector <T> > &matrix,
1832  const bool transpose = false,
1833  const int precision = 5
1834  ){
1835  if(1 > matrix.size()){
1836  throw std::runtime_error(
1837  ai::string("Exception while printing the matrix: ")
1838  + ai::string("size should be at least 1.")
1839  );
1840  }
1841 
1842  std::cout << std::scientific;
1843  std::cout.precision(precision);
1844 
1845  std::cout << "Matrix[" << matrix.size() << "x" << matrix[0].size()
1846  << "] = {" << std::endl;
1847 
1848  if(transpose){
1849  for(std::size_t j = 0; j < matrix[0].size(); ++j){
1850  const std::size_t lastIndex = matrix.size() - 1;
1851 
1852  for(std::size_t i = 0; i < lastIndex; ++i){
1853  std::cout << matrix[i][j] << ", ";
1854  }
1855 
1856  std::cout << matrix[lastIndex][j] << std::endl;
1857  }
1858  }else{
1859  for(std::size_t i = 0; i < matrix.size(); ++i){
1860  const std::size_t lastIndex = matrix[i].size() - 1;
1861 
1862  for(std::size_t j = 0; j < lastIndex; ++j){
1863  std::cout << matrix[i][j] << ", ";
1864  }
1865 
1866  std::cout << matrix[i][lastIndex] << std::endl;
1867  }
1868  }
1869 
1870  std::cout << "}[" << matrix.size() << "x" << matrix[0].size()
1871  << "]" << std::endl;
1872  }
1873 
1876  template<typename T>
1878  const std::vector<T> &vector,
1879  const int precision = 5
1880  ){
1881  if(1 > vector.size()){
1882  throw std::runtime_error(
1883  ai::string("Exception while printing the vector: ")
1884  + ai::string("size should be at least 1.")
1885  );
1886  }
1887 
1888  std::size_t lastIndex = vector.size() - 1;
1889 
1890  std::cout << std::scientific;
1891  std::cout.precision(precision);
1892 
1893  std::cout << "Vector[" << vector.size() << "] = {" << std::endl;
1894 
1895  for(std::size_t i = 0; i < lastIndex; ++i){
1896  std::cout << vector[i] << ", ";
1897  }
1898  std::cout << vector[lastIndex] << std::endl;
1899 
1900  std::cout << "}[" << vector.size() << "]" << std::endl;
1901  }
1902 
1905  template<typename T>
1907  const std::vector<std::vector <T> > &matrix,
1908  const bool transpose = false,
1909  const int precision = 5
1910  ){
1911  ai::printMatrix(matrix, transpose, precision);
1912  }
1913 
1916  template<typename T>
1918  const std::vector<T> &vector,
1919  const int precision = 5
1920  ){
1921  ai::printVector(vector, precision);
1922  }
1923 
1926  template<typename T>
1928  const T value,
1929  const std::string name = std::string("Value")
1930  ){
1931  std::cout << name << " = " << value << std::endl;
1932  }
1933 
1936  static std::string black("\033[30m");
1937 
1940  static std::string red("\033[31m");
1941 
1944  static std::string green("\033[32m");
1945 
1948  static std::string yellow("\033[33m");
1949 
1952  static std::string blue("\033[34m");
1953 
1956  static std::string magenta("\033[35m");
1957 
1960  static std::string cyan("\033[36m");
1961 
1964  static std::string white("\033[37m");
1965 
1968  static std::string bold("\033[1m");
1969 
1972  static std::string underline("\033[4m");
1973 
1977  static std::string reset("\033[0m");
1978 
1979  //isatty
1982  template<typename T>
1983  INLINE void printStyle(const T income, const std::string style){
1984  std::cout << style << income << ai::reset << std::endl;
1985  }
1986 
1989  template<typename T>
1990  INLINE void printBlack(const T income){
1991  ai::printStyle(income, ai::black);
1992  }
1993 
1996  template<typename T>
1997  INLINE void printRed(const T income){
1998  ai::printStyle(income, ai::red);
1999  }
2000 
2003  template<typename T>
2004  INLINE void printGreen(const T income){
2005  ai::printStyle(income, ai::green);
2006  }
2007 
2010  template<typename T>
2011  INLINE void printYellow(const T income){
2012  ai::printStyle(income, ai::yellow);
2013  }
2014 
2017  template<typename T>
2018  INLINE void printBlue(const T income){
2019  ai::printStyle(income, ai::blue);
2020  }
2021 
2024  template<typename T>
2025  INLINE void printMagenta(const T income){
2026  ai::printStyle(income, ai::magenta);
2027  }
2028 
2031  template<typename T>
2032  INLINE void printCyan(const T income){
2033  ai::printStyle(income, ai::cyan);
2034  }
2035 
2038  template<typename T>
2039  INLINE void printWhite(const T income){
2040  ai::printStyle(income, ai::white);
2041  }
2042 
2045  template<typename T>
2046  INLINE void printBold(const T income){
2047  ai::printStyle(income, ai::bold);
2048  }
2049 
2052  template<typename T>
2053  INLINE void printUnderline(const T income){
2054  ai::printStyle(income, ai::underline);
2055  }
2056 
2059  auto printStyleTest = [](
2060  const std::string color,
2061  const std::string colorName
2062  ) -> void{
2063  std::cout << colorName << ": " << color << "normal, " << ai::bold
2064  << "bold " << ai::reset
2065  << color << " and " << ai::underline << "underline"
2066  << ai::reset
2067  << color << "." << ai::reset
2068  << std::endl;
2069  };
2070 
2071  printStyleTest(ai::black, "Black");
2072  printStyleTest(ai::red, "Red");
2073  printStyleTest(ai::green, "Green");
2074  printStyleTest(ai::yellow, "Yellow");
2075  printStyleTest(ai::blue, "Blue");
2076  printStyleTest(ai::magenta, "Magenta");
2077  printStyleTest(ai::cyan, "Cyan");
2078  printStyleTest(ai::white, "White");
2079  }
2080 
2083  ai::black = std::string();
2084  ai::red = std::string();
2085  ai::green = std::string();
2086  ai::yellow = std::string();
2087  ai::blue = std::string();
2089  ai::cyan = std::string();
2090  ai::white = std::string();
2091  ai::bold = std::string();
2093  ai::reset = std::string();
2094  }
2095 
2097 
2103 
2107  template<typename T>
2109  const std::string filename,
2110  const std::vector<std::vector <T> > &matrix,
2111  std::string comment = std::string(),
2112  const bool transpose = false,
2113  std::string type = std::string("text"),
2114  std::string delimiter = std::string(" "),
2115  const std::size_t tokenWidth = 14
2116  ){
2117  std::string extension("_m.txt");
2118  std::string prefix("");
2119  std::string suffix("");
2120 
2121  if(std::string("wolfram") == type){
2122  extension = std::string("_m.wm");
2123  prefix = std::string("{");
2124  delimiter = std::string(", ");
2125  suffix = std::string("}");
2126  }
2127 
2128  if(std::string("excel") == type){
2129  extension = std::string("_m.csv");
2130  delimiter = std::string("; ");
2131  }
2132 
2133  if(std::string("data") == type){
2134  extension = std::string("_m.dat");
2135  delimiter = std::string("\t");
2136  }
2137 
2138  std::ofstream output(filename + extension);
2139 
2140  if(!output.good()){
2141  throw std::runtime_error(
2142  ai::string("Exception while saving the matrix into the file: ")
2143  + filename
2144  );
2145  }
2146 
2147  if(std::string() != comment){
2148  output << comment << std::endl;
2149  }
2150 
2151  output << prefix;
2152 
2153  if(transpose){
2154  for(std::size_t j = 0; j < matrix[0].size(); ++j){
2155  output << prefix;
2156 
2157  const std::size_t lastIndex = matrix.size() - 1;
2158 
2159  for(std::size_t i = 0; i < lastIndex; ++i){
2160  output << std::setw(tokenWidth) << matrix[i][j]
2161  << delimiter;
2162  }
2163 
2164  output << std::setw(tokenWidth) << matrix[lastIndex][j]
2165  << suffix << std::endl;
2166  }
2167  }else{
2168  for(std::size_t i = 0; i < matrix.size(); ++i){
2169  output << prefix;
2170 
2171  const std::size_t lastIndex = matrix[i].size() - 1;
2172 
2173  for(std::size_t j = 0; j < lastIndex; ++j){
2174  output << std::setw(tokenWidth) << matrix[i][j]
2175  << delimiter;
2176  }
2177 
2178  output << std::setw(tokenWidth) << matrix[i][lastIndex]
2179  << suffix << std::endl;
2180  }
2181  }
2182 
2183  output << suffix;
2184 
2185  output.close();
2186  }
2187 
2191  template<typename T>
2193  const std::string filename,
2194  const std::vector<T> &vector,
2195  std::string comment = std::string(),
2196  std::string type = std::string("text"),
2197  std::string delimiter = std::string("\n")
2198  ){
2199  std::string extension("_v.txt");
2200  std::string prefix("");
2201  std::string suffix("");
2202 
2203  if(std::string("wolfram") == type){
2204  extension = std::string("_v.wm");
2205  prefix = std::string("{");
2206  delimiter = std::string(", ");
2207  suffix = std::string("}");
2208  }
2209 
2210  if(std::string("excel") == type){
2211  extension = std::string("_v.csv");
2212  delimiter = std::string("; ");
2213  }
2214 
2215  if(std::string("data") == type){
2216  extension = std::string("_v.dat");
2217  delimiter = std::string("\t");
2218  }
2219 
2220  std::ofstream output(filename + extension);
2221 
2222  if(!output.good()){
2223  throw std::runtime_error(
2224  ai::string("Exception while saving the vector into the file: ")
2225  + filename
2226  );
2227  }
2228 
2229  if(std::string() != comment){
2230  output << comment << std::endl;
2231  }
2232 
2233  output << prefix;
2234 
2235  const std::size_t lastIndex = vector.size() - 1;
2236 
2237  for(std::size_t i = 0; i < lastIndex; ++i){
2238  output << vector[i] << delimiter;
2239  }
2240 
2241  output << vector[lastIndex] << suffix;
2242 
2243  output.close();
2244  }
2245 
2249  const std::string filename,
2250  const std::string line,
2251  std::string comment = std::string()
2252  ){
2253  std::ofstream output(filename + "_l.txt");
2254 
2255  if(!output.good()){
2256  throw std::runtime_error(
2257  ai::string("Exception while saving the line into the file: ")
2258  + filename
2259  );
2260  }
2261 
2262  if(std::string() != comment){
2263  output << comment << "\n";
2264  }
2265 
2266  output << line << std::endl;
2267 
2268  output.close();
2269  }
2270 
2272  template<typename T>
2273  INLINE void save(
2274  const std::string filename,
2275  const std::vector<std::vector <T> > &matrix,
2276  std::string comment = std::string()
2277  ){
2278  ai::saveMatrix(filename, matrix, comment);
2279  }
2280 
2282  template<typename T>
2283  INLINE void save(
2284  const std::string filename,
2285  const std::vector<T> &vector,
2286  std::string comment = std::string()
2287  ){
2288  ai::saveVector(filename, vector, comment);
2289  }
2290 
2292  template<typename T>
2293  INLINE void save(
2294  const std::string filename,
2295  const std::string line,
2296  std::string comment = std::string()
2297  ){
2298  ai::saveLine(filename, line, comment);
2299  }
2300 
2301  #if defined(AI_GCC5_SUPPORT)
2302  INLINE void saveLog(
2305  const std::string filename,
2306  std::string log,
2307  const bool timestamp = false,
2308  const std::string stampSeparator = std::string(" ")
2309  ){
2310  std::ofstream output(filename, std::ios_base::app);
2311 
2312  if(!output.good()){
2313  throw std::runtime_error(
2314  ai::string("Exception while saving log into the file: ")
2315  + filename
2316  );
2317  }
2318 
2319  if(timestamp){
2320  output << ai::getDateAndTime() << stampSeparator;
2321  }
2322 
2323  output << log << std::endl;
2324 
2325  output.close();
2326  }
2327 
2331  const std::string filename,
2332  std::vector<std::string> &logs,
2333  const bool timestamp = false,
2334  const std::string stampSeparator = std::string(" ")
2335  ){
2336  std::ofstream output(filename, std::ios_base::app);
2337 
2338  if(!output.good()){
2339  throw std::runtime_error(
2340  ai::string("Exception while saving log into the file: ")
2341  + filename
2342  );
2343  }
2344 
2345  std::string prefix("");
2346 
2347  if(timestamp){
2348  prefix = ai::getDateAndTime() + stampSeparator;
2349  }
2350 
2351  for(std::size_t i = 0; i < logs.size(); ++i){
2352  output << prefix << logs[i] << std::endl;
2353  }
2354 
2355  output.close();
2356  }
2357 
2358  #endif
2359 
2363  template<typename T>
2365  const std::string filename,
2366  std::vector< std::vector<T> > &positions,
2367  double &radius
2368  ){
2369  std::ifstream input(filename, std::ios::binary | std::ios::in);
2370 
2371  if(!input.good()){
2372  throw std::runtime_error(
2373  ai::string("Exception while reading positions from the file: ")
2374  + filename
2375  );
2376  }
2377 
2378  char numberOfParticlesValue[4];
2379  char startByte[4];
2380  char radiusValue[8];
2381  char value[4];
2382 
2383  input.seekg(4);
2384  input.read(numberOfParticlesValue, 4);
2385  input.read(startByte, 4);
2386  input.seekg(24);
2387  input.read(radiusValue, 8);
2388  input.seekg(reinterpret_cast<int&>(startByte));
2389 
2390  radius = reinterpret_cast<double&>(radiusValue);
2391 
2392  std::size_t numberOfParticles = (std::size_t) reinterpret_cast<int&>(
2393  numberOfParticlesValue
2394  );
2395 
2396  positions.resize(numberOfParticles);
2397 
2398  for(std::size_t i = 0; i < numberOfParticles; ++i){
2399  positions[i].resize(3);
2400 
2401  for(std::size_t j = 0; j < 3; ++j){
2402  input.read(value, 4);
2403  positions[i][j] = (T) reinterpret_cast<float&>(value);
2404  }
2405 
2406  std::cout << std::endl;
2407  }
2408 
2409  input.close();
2410 
2411  return true;
2412  }
2413 
2417  template<typename T>
2419  const std::string filename,
2420  const std::vector< std::vector<T> > &positions,
2421  const double radius = 1
2422  ){
2423  std::ofstream output(
2424  filename + std::string(".a3r"), std::ios::binary | std::ios::out
2425  );
2426 
2427  if(!output.good()){
2428  throw std::runtime_error(
2429  ai::string("Exception while saving positions into the file: ")
2430  + filename
2431  );
2432  }
2433 
2434  const std::size_t numberOfParticles = positions.size();
2435 
2436  const int integerNumberOfParticles = (int) numberOfParticles;
2437 
2438  const int startByte = 36;
2439  const int futureValue = 0;
2440 
2441  const int intSize = 4;
2442  const int floatSize = 4;
2443  const int doubleSize = 8;
2444 
2445  output.write("a3r\0", 4);
2446  output.write((char*) &integerNumberOfParticles, intSize);
2447  output.write((char*) &startByte, intSize);
2448  output.write("AiLib 1.1.0\0", 12);
2449  output.write((char*) &radius, doubleSize);
2450  output.write((char*) &futureValue, intSize);
2451 
2452  if(2 == positions[0].size()){
2453  for(std::size_t i = 0; i < numberOfParticles; ++i){
2454  float x = (float) positions[i][0];
2455  float y = (float) positions[i][1];
2456  float z = 0.;
2457 
2458  output.write((char*) &x, floatSize);
2459  output.write((char*) &y, floatSize);
2460  output.write((char*) &z, floatSize);
2461  }
2462  }else{
2463  if(3 == positions[0].size()){
2464  for(std::size_t i = 0; i < numberOfParticles; ++i){
2465  float x = (float) positions[i][0];
2466  float y = (float) positions[i][1];
2467  float z = (float) positions[i][2];
2468 
2469  output.write((char*) &x, floatSize);
2470  output.write((char*) &y, floatSize);
2471  output.write((char*) &z, floatSize);
2472  }
2473  }else{
2474  return false;
2475  }
2476  }
2477 
2478  output.close();
2479 
2480  return true;
2481  }
2482 
2487  template<typename T>
2489  const std::string filename,
2490  std::vector< std::vector<T> > &matrix
2491  ){
2492  std::ifstream input(filename);
2493 
2494  if(!input.good()){
2495  throw std::runtime_error(
2496  ai::string("Exception while reading positions from the file: ")
2497  + filename
2498  );
2499  }
2500 
2501  std::size_t counter = 0;
2502 
2503  std::string token;
2504 
2505  T value;
2506 
2507  for(std::string line; std::getline(input, line);){
2508  ++counter;
2509 
2510  if(3 > counter){
2511  continue;
2512  }
2513 
2514  std::istringstream stream(line);
2515 
2516  std::vector<T> row;
2517 
2518  std::size_t subCounter = 0;
2519 
2520  while(std::getline(stream, token, ' ')){
2521  ++subCounter;
2522  if(2 > subCounter){
2523  continue;
2524  }
2525  if(std::istringstream(token) >> value){
2526  row.push_back(value);
2527  }
2528  }
2529 
2530  matrix.push_back(row);
2531  }
2532 
2533  input.close();
2534  }
2535 
2539  template<typename T>
2541  const std::string filename,
2542  const std::vector< std::vector<T> > &matrix,
2543  const std::vector<T> &tones,
2544  std::string elementName = "C"
2545  ){
2546  std::ofstream output(filename + std::string(".xyz"));
2547 
2548  if(!output.good()){
2549  throw std::runtime_error(
2550  ai::string("Exception while saving positions into the file: ")
2551  + filename
2552  );
2553  }
2554 
2555  const std::size_t numberOfParticles = matrix.size();
2556 
2557  bool withColors = (tones.size() == numberOfParticles);
2558 
2559  output << numberOfParticles << std::endl << std::endl;
2560 
2561  for(std::size_t i = 0; i < numberOfParticles; ++i){
2562  output << elementName;
2563 
2564  for(std::size_t j = 0; j < matrix[i].size(); ++j){
2565  output << " " << matrix[i][j];
2566  }
2567 
2568  if(withColors){
2569  double color = 1. - 2. * tones[i];
2570 
2571  if(1. < color){
2572  color = 1.;
2573  }else{
2574  if(0. > color){
2575  color = 0.;
2576  }
2577  }
2578 
2579  output << " " << color;
2580 
2581  color = 1. - std::abs(2. * tones[i] - 1.);
2582 
2583  if(1. < color){
2584  color = 1.;
2585  }else{
2586  if(0. > color){
2587  color = 0.;
2588  }
2589  }
2590 
2591  output << " " << color;
2592 
2593  color = 2. * tones[i] - 1.;
2594 
2595  if(1. < color){
2596  color = 1.;
2597  }else{
2598  if(0. > color){
2599  color = 0.;
2600  }
2601  }
2602 
2603  output << " " << color;
2604  }
2605 
2606  output << std::endl;
2607  }
2608 
2609  output.close();
2610  }
2611 
2614  template<typename T>
2616  const std::string filename,
2617  const std::vector< std::vector<T> > &matrix,
2618  std::string elementName = "C"
2619  ){
2620  saveXYZ(filename, matrix, std::vector<T>(), elementName);
2621  }
2622 
2624 
2629 
2637  INLINE bool folderExists(const std::string name){
2638  struct stat buffer;
2639 
2640  return 0 == stat(name.c_str(), &buffer);
2641  }
2642 
2655  const std::string filename,
2656  const std::string token = std::string()
2657  ){
2658  std::ifstream input(filename);
2659 
2660  if(!input.good()){
2661  throw std::runtime_error(
2662  ai::string("Exception while counting lines in the file: ")
2663  + filename
2664  );
2665  }
2666 
2667  std::size_t count = 0;
2668 
2669  if(std::string() == token){
2670  for(std::string line; getline(input, line);){
2671  ++count;
2672  }
2673  }else{
2674  for(std::string line; getline(input, line);){
2675  if(std::string::npos != line.find(token)){
2676  ++count;
2677  }
2678  }
2679  }
2680 
2681  input.close();
2682 
2683  return count;
2684  }
2685 
2686  #if defined(AI_DIRENT_SUPPORT)
2687  INLINE std::vector<std::string> listFilesWithExtension(
2689  std::string path,
2690  const std::string extension,
2691  const std::string prefix = std::string(),
2692  const bool addPathToFileNames = false
2693  ){
2694  DIR *dir;
2695 
2696  struct dirent *ent;
2697 
2698  dir = opendir(path.c_str());
2699 
2700  std::vector<std::string> files;
2701 
2702  if(NULL != dir){
2703  while(NULL != (ent = readdir (dir))){
2704  if(
2705  DT_REG == ent->d_type
2706  && hasSuffix(ent->d_name, extension)
2707  ){
2708  files.push_back(prefix + ent->d_name);
2709  }
2710  }
2711 
2712  closedir(dir);
2713  }
2714 
2715  if(addPathToFileNames){
2716  path += std::string("/");
2717 
2718  for(std::size_t i = 0; i < files.size(); ++i){
2719  files[i] = path + files[i];
2720  }
2721  }
2722 
2723  return files;
2724  }
2725  #endif
2726 
2728 
2729  #if defined(AI_SHELL_SUPPORT)
2730 
2738  const std::string command
2739  ){
2740  const std::size_t bufferSize = 128;
2741 
2742  std::array<char, bufferSize> buffer;
2743 
2744  std::string result;
2745 
2746  std::shared_ptr<FILE> pipe(popen(command.c_str(), "r"), pclose);
2747 
2748  if(!pipe){
2749  throw std::runtime_error(
2750  ai::string("Exception while executing the command: ")
2751  + command
2752  );
2753  }
2754 
2755  while(!feof(pipe.get())){
2756  if(nullptr != fgets(buffer.data(), bufferSize, pipe.get())){
2757  result += buffer.data();
2758  }
2759  }
2760 
2761  return result;
2762  }
2763 
2765 
2766  #endif
2767 
2768 }
2769 
2771 
2772 #if defined(AI_FUTURE)
2773  namespace ai{
2776  INLINE bool createFolder(const std::string name);
2777  }
2778 #endif
2779 
2780 #endif
INLINE bool assignStringParameter(const char *input, const std::string name, std::string &value)
Definition: ai.hh:1483
#define INLINE
If defined, funstions will be marked as inline.
Definition: ai.hh:19
INLINE void parseFileIntoString(const std::string filename, std::string &content)
Definition: ai.hh:1754
INLINE void printLine(const std::string line, const int screenWidth=80)
Definition: ai.hh:1636
static std::string underline("\3[4m")
Terminal style code for underline.
INLINE void printStyle(const T income, const std::string style)
Definition: ai.hh:1983
INLINE void translateVectorIntoSquareMatrix(std::vector< T > &vector, std::vector< std::vector< T > > &matrix)
Transform vector into a square matrix (if possible)
Definition: ai.hh:757
INLINE void printCyan(const T income)
Definition: ai.hh:2032
INLINE std::size_t counter(const std::size_t value=0)
Returns ID starting from zero or the specified value.
Definition: ai.hh:314
INLINE void saveLog(const std::string filename, std::string log, const bool timestamp=false, const std::string stampSeparator=std::string(" "))
Definition: ai.hh:2304
INLINE void saveMatrix(const std::string filename, const std::vector< std::vector< T > > &matrix, std::string comment=std::string(), const bool transpose=false, std::string type=std::string("text"), std::string delimiter=std::string(" "), const std::size_t tokenWidth=14)
Definition: ai.hh:2108
INLINE void saveVector(const std::string filename, const std::vector< T > &vector, std::string comment=std::string(), std::string type=std::string("text"), std::string delimiter=std::string("\))
Definition: ai.hh:2192
INLINE T min(const std::vector< std::vector< T > > &input)
Returns minimum of matrix values.
Definition: ai.hh:466
INLINE void printBlack(const T income)
Definition: ai.hh:1990
INLINE void generateRandomMatrix(std::vector< std::vector< T > > &matrix, const std::size_t xSize, const std::size_t ySize, const T min=std::numeric_limits< T >::min(), const T max=std::numeric_limits< T >::max())
Fill matrix with random values.
Definition: ai.hh:584
INLINE bool equal(const char *charString, const std::string string1)
Checks if a char string is equal to a std::string.
Definition: ai.hh:237
INLINE std::string parseParameter(const char *input, const std::string name)
Definition: ai.hh:1394
INLINE void printUnderline(const T income)
Definition: ai.hh:2053
static std::string black("\3[30m")
Terminal color code for black.
INLINE std::string execute(const std::string command)
Definition: ai.hh:2737
INLINE void clearStyles()
Definition: ai.hh:2082
INLINE std::string marker(const std::size_t value=0)
Returns a string containing the word "Marker" and its ID.
Definition: ai.hh:334
INLINE std::string getTime(std::chrono::system_clock::time_point timePoint=std::chrono::system_clock::now())
Get time.
Definition: ai.hh:1370
INLINE void multiply(const std::vector< std::vector< T > > &left, const std::vector< std::vector< T > > &right, std::vector< std::vector< T > > &result)
Definition: ai.hh:872
INLINE void printRed(const T income)
Definition: ai.hh:1997
INLINE void printMatrix(const std::vector< std::vector< T > > &matrix, const bool transpose=false, const int precision=5)
Definition: ai.hh:1830
INLINE void printBold(const T income)
Definition: ai.hh:2046
INLINE void printMagenta(const T income)
Definition: ai.hh:2025
INLINE void printGreen(const T income)
Definition: ai.hh:2004
INLINE void printAllStyles()
Definition: ai.hh:2058
INLINE void clearScreen()
Definition: ai.hh:1565
INLINE void saveXYZ(const std::string filename, const std::vector< std::vector< T > > &matrix, const std::vector< T > &tones, std::string elementName="C")
Definition: ai.hh:2540
INLINE void multiplyComplexElementWise(const std::vector< std::vector< T > > &left, const std::vector< std::vector< T > > &right, std::vector< std::vector< T > > &result)
Definition: ai.hh:1068
Main namespace.
INLINE std::vector< std::string > listFilesWithExtension(std::string path, const std::string extension, const std::string prefix=std::string(), const bool addPathToFileNames=false)
Definition: ai.hh:2688
INLINE void printBlue(const T income)
Definition: ai.hh:2018
INLINE std::string complexIntoString(const std::vector< T > complexValue)
Definition: ai.hh:1100
INLINE void save(const std::string filename, const std::vector< std::vector< T > > &matrix, std::string comment=std::string())
Definition: ai.hh:2273
static std::string white("\3[37m")
Terminal color code for white.
void rotateMatrix(std::vector< std::vector< T > > &matrix, const bool rotateClockwise=false)
Rotate square matrix.
Definition: ai.hh:637
INLINE bool isSquare(const T value)
Checks if number is square.
Definition: ai.hh:507
INLINE void ifft(std::vector< std::vector< T > > &complexVector)
Definition: ai.hh:1194
INLINE void fft(std::vector< std::vector< T > > &complexVector)
Definition: ai.hh:1119
INLINE std::string getVersion()
Get version of the library.
Definition: ai.hh:112
INLINE void parseFileInMatrix(const std::string filename, const char separator, std::vector< std::vector< T > > &matrix)
Definition: ai.hh:1664
INLINE bool assignBooleanParameter(const char *input, const std::string name, bool &value)
Definition: ai.hh:1445
static std::string reset("\3[0m")
Terminal code to reset special formatting.
INLINE bool contains(const std::string &text, const std::string &substring)
Checks if a string contains a substring.
Definition: ai.hh:173
INLINE void accumulateFileInMatrix(const std::string filename, const char separator, std::vector< std::vector< T > > &matrix)
Definition: ai.hh:1777
INLINE void showProgressBar(double progress, const int screenWidth=80)
Definition: ai.hh:1593
INLINE void setLocale(const std::string locale)
Definition: ai.hh:1570
INLINE T min(const T a, const T b)
Returns minimum of two values.
Definition: ai.hh:395
INLINE std::string prependNumber(const T value, const std::size_t symbolsBeforePoint, const char symbolToPrepend='0')
Definition: ai.hh:282
INLINE void printMarker(const std::size_t value=0)
Calls marker() and prints result to stdout.
Definition: ai.hh:351
INLINE bool assignAbsDoubleParameter(const char *input, const std::string name, double &value)
Definition: ai.hh:1521
INLINE std::string toUpperCase(std::string input)
Convert a string to upper case.
Definition: ai.hh:250
INLINE bool assignParameter(const char *input, const std::string name, T &value)
Definition: ai.hh:1502
INLINE std::string getDate(std::chrono::system_clock::time_point timePoint=std::chrono::system_clock::now())
Get date.
Definition: ai.hh:1348
INLINE void conjugate(std::vector< std::vector< T > > &complexVector)
Definition: ai.hh:1108
static std::string cyan("\3[36m")
Terminal color code for cyan.
INLINE bool assignCharParameter(const char *input, const std::string name, char &value)
Definition: ai.hh:1460
INLINE std::chrono::high_resolution_clock::time_point time()
Returns current time point.
Definition: ai.hh:1222
INLINE void loadXYZ(const std::string filename, std::vector< std::vector< T > > &matrix)
Definition: ai.hh:2488
static const double e
Mathematical constant &#39;e&#39;.
Definition: ai.hh:365
INLINE void assignFromVectorByIntervalCondition(T &value, const T parameter, const std::vector< std::vector< T > > intervals)
Definition: ai.hh:1411
INLINE void printVector(const std::vector< T > &vector, const int precision=5)
Definition: ai.hh:1877
INLINE void inverseMatrix(std::vector< std::vector< T > > matrix, std::vector< std::vector< T > > &inverse)
Definition: ai.hh:674
static const double pi
Mathematical constant &#39;pi&#39;.
Definition: ai.hh:369
static std::string green("\3[32m")
Terminal color code for green.
INLINE bool assignByCheckingParameter(const char *input, const std::string parameter, T &value, const T supposed)
Definition: ai.hh:1541
INLINE void saveLine(const std::string filename, const std::string line, std::string comment=std::string())
Definition: ai.hh:2248
INLINE std::chrono::system_clock::time_point systemTime()
Returns current time point.
Definition: ai.hh:1231
static std::string yellow("\3[33m")
Terminal color code for yellow.
INLINE void generateCirculantMatrix(std::vector< std::vector< T > > &matrix, std::vector< T > &source, const bool moveToTheRight=true)
Definition: ai.hh:796
INLINE void translateMatrixIntoVector(std::vector< std::vector< T > > &matrix, std::vector< T > &vector)
Elongates matrix into a vector.
Definition: ai.hh:735
INLINE std::size_t countLinesInFile(const std::string filename, const std::string token=std::string())
Definition: ai.hh:2654
INLINE bool folderExists(const std::string name)
Check if folder exists.
Definition: ai.hh:2637
INLINE void print(const std::vector< std::vector< T > > &matrix, const bool transpose=false, const int precision=5)
Definition: ai.hh:1906
INLINE void printDuration(const std::chrono::high_resolution_clock::time_point start, const std::chrono::high_resolution_clock::time_point finish, const std::string scale=std::string("ms"), const std::size_t count=0)
Definition: ai.hh:1293
INLINE double duration(const std::chrono::high_resolution_clock::time_point start, const std::chrono::high_resolution_clock::time_point finish, const std::string scale=std::string("ms"))
Definition: ai.hh:1250
INLINE void accumulateFileInVector(const std::string filename, const char separator, std::vector< T > &vector, const bool checkForNaN=false)
Definition: ai.hh:1800
INLINE bool saveA3R(const std::string filename, const std::vector< std::vector< T > > &positions, const double radius=1)
Definition: ai.hh:2418
INLINE std::string getDateAndTime(std::chrono::system_clock::time_point timePoint=std::chrono::system_clock::now())
Get date and time.
Definition: ai.hh:1326
INLINE void applyReplace(std::string &text, const std::string &substring, const std::string &replacement)
Modifies your string by replacing all occurrences of a substring string with your text...
Definition: ai.hh:216
INLINE bool hasSuffix(const std::string &text, const std::string &suffix)
Checks if a string ends with a substring.
Definition: ai.hh:157
INLINE std::string string(const T value)
Converts input into a string.
Definition: ai.hh:132
INLINE std::string toLowerCase(std::string input)
Convert a string to lower case.
Definition: ai.hh:263
INLINE std::string replace(std::string text, const std::string &substring, const std::string &replacement)
Replaces all occurrences of a substring in a copy of the initial string with your text...
Definition: ai.hh:191
INLINE T max(const std::vector< std::vector< T > > &input)
Returns maximum of matrix values.
Definition: ai.hh:487
INLINE void parseFileInVector(const std::string filename, const char separator, std::vector< T > &vector)
Definition: ai.hh:1707
INLINE void printWhite(const T income)
Definition: ai.hh:2039
INLINE T sign(const T value)
Returns signum of the value.
Definition: ai.hh:379
INLINE void generateRandomVector(std::vector< T > &vector, const std::size_t length, const T min=std::numeric_limits< T >::min(), const T max=std::numeric_limits< T >::max())
Definition: ai.hh:542
static std::string bold("\3[1m")
Terminal style code for bold.
static std::string red("\3[31m")
Terminal color code for red.
INLINE bool hasPrefix(const std::string &text, const std::string &prefix)
Checks if a string begins with a substring.
Definition: ai.hh:146
INLINE void multiplyElementWise(const std::vector< std::vector< T > > &left, const std::vector< std::vector< T > > &right, std::vector< std::vector< T > > &result)
Definition: ai.hh:1003
INLINE bool loadA3R(const std::string filename, std::vector< std::vector< T > > &positions, double &radius)
Definition: ai.hh:2364
INLINE T max(const T a, const T b)
Returns maximum of two values.
Definition: ai.hh:411
INLINE void printYellow(const T income)
Definition: ai.hh:2011
static std::string blue("\3[34m")
Terminal color code for blue.
static std::string magenta("\3[35m")
Terminal color code for magenta.