// TODO:
// I'm using wrong algorithm, should use http://www.computer.org/csdl/proceedings/hicss/2003/1874/09/187490332a.pdf
// sort output by content type

package csci599;

import java.io.*;
import java.util.*;
import java.util.function.*;
import static java.util.stream.Collectors.*;

public class FHT {
    private static final int H = 16;
    private static int[][] matrix;
    private static int numFiles = 0; // don't use fileNames.length in case can't open some files

    public static void analyze(File folder, List<String> contentTypes) {
        // create sparse matrix
        matrix = new int[H][256];
        numFiles = 0;
        FileTypeFilter.forEach(folder, contentTypes, (file, contentType) -> {
            try (FileInputStream in = new FileInputStream(file)) {
                numFiles++;
                for (int j = 0; j < H; j++) {
                    int b = in.read();
                    if (b < 0) break;
                    matrix[j][b]++;
                }
            } catch (IOException ex) {
                System.err.println("Error reading file: " + file.getPath());
            }
        });
        if (numFiles == 0) {
            System.out.println("Folder is empty.");
            return;
        }
        // helper function to convert matrix row into string
        final double finalNumFiles = numFiles;
        Function<int[], String> rowString = row -> Arrays.stream(row).mapToObj(c -> "" + c / finalNumFiles).collect(joining(","));
        // write csv file
        try (Writer out = new OutputStreamWriter(new FileOutputStream("fht.csv"), "UTF-8")) {
            for (int[] row : matrix) {
                out.write(rowString.apply(row) + "\n");
            }
        } catch (IOException ex) {
            System.err.println("Error writing fht.csv");
        }
        // write json file
        try (Writer out = new OutputStreamWriter(new FileOutputStream("fht.json"), "UTF-8")) {
            out.write("[\n");
            for (int[] row : matrix) {
                out.write("    [" + rowString.apply(row) + "],\n");
            }
            out.write("]\n");
        } catch (IOException ex) {
            System.err.println("Error writing fht.json");
        }
    }
}

@@ -833,23 +833,23 @@
 int 
-j
+i
  = 0; 
-j
+i
  %3C H; 
-j
+i
 ++) 
@@ -919,20 +919,203 @@
  (b 
-%3C
+%3E=
  0) 
-break;%0A
+%7B%0A                        matrix%5Bi%5D%5Bb%5D++;%0A                    %7D else %7B%0A                        // end of file, subtract 1 from rows%0A                        for (int j = 0; j %3C 256; j++) %7B%0A 
     
@@ -1134,23 +1134,78 @@
     
+       
 matrix%5B
-j%5D%5Bb%5D++;
+i%5D%5Bj%5D--;%0A                        %7D%0A                    %7D
 %0A   
@@ -1464,32 +1464,32 @@
 turn;%0A        %7D%0A
-
         // helpe
@@ -1533,16 +1533,109 @@
  string%0A
+        // dividing by numFiles here is equivalent to fingerprint formula in II.3.2 of paper%0A
         

subtract 1 from FHT row if end of file