1 module dnum.csv;
2 
3 import dnum.tensor;
4 
5 import std.file : readText, write;
6 import std.array : split, join;
7 import std.conv : to;
8 import std.string : chop;
9 import std.algorithm : map;
10 
11 alias Header = string[];
12 
13 /++
14   DataFrame - readcsv or writecsv structure
15 +/
16 struct DataFrame {
17   Header header;
18   Tensor data;
19 
20   this(Header h, Tensor t) {
21     this.header = h;
22     this.data = t;
23   }
24 
25   this(Tensor t) {
26     this.data = t;
27 
28     Header h;
29     h.length = t.ncol;
30     foreach (i, ref head; h) {
31       head = to!string(i);
32     }
33     this.header = h;
34   }
35 
36   // TODO : Implement Print
37   // TODO : Override Index (with Header)
38 }
39 
40 /++
41   readcsv - Read CSV file to DataFrame
42 +/
43 DataFrame readcsv(string filename, bool header = false) {
44   auto file = readText(filename).chop;
45   auto temp = file.split("\n");
46 
47   Header head;
48 
49   if (header) {
50     head = temp[0].split(",");
51     temp = temp[1 .. $][];
52   }
53 
54   double[][] container;
55   container.length = temp.length;
56   
57   foreach (i; 0.. temp.length) {
58     auto values = temp[i].split(",");
59     auto l = values.length;
60     container[i].length = l;
61     foreach (j; 0 .. l) {
62       container[i][j] = values[j].to!double;
63     }
64   }
65   if (header) {
66     return DataFrame(head, Tensor(container));
67   } else {
68     return DataFrame(Tensor(container));
69   }
70 }
71 
72 /++
73   writecsv - Write DataFrame to CSV file
74 +/
75 void writecsv(string filename, DataFrame df, bool header = false) {
76   Header head = [ df.header.join(",") ];
77   double[][] target = df.data.data;
78 
79   string[] container;
80   container.length = target.length;
81 
82   foreach (i; 0 .. target.length) {
83     container[i] = target[i].map!(to!string).join(",");
84   }
85   
86   if (!header) {
87     string toWrite = container.join("\n");
88     write(filename, toWrite);
89   } else {
90     string[] forWrite = join([head, container]);
91     string toWrite = forWrite.join("\n");
92     write(filename, toWrite);
93   }
94 }