/*
 * BandNWAlign.cpp
 *
 *  Created on: Nov 16, 2014
 *      Author: qimao
 */

#ifndef SPARSE_MATRIX_H_
#define SPARSE_MATRIX_H_

#include <seqan/sequence.h>
#include <seqan/stream.h>
#include <seqan/seq_io.h>

#include <unordered_map>
#include <unordered_set>

#include <armadillo>
#include "aligner.h"

using namespace arma;
/*
 * Note: the hash combination method might not be a good method
 * http://stackoverflow.com/questions/4870437/pairint-int-pair-as-key-of-unordered-map-issue
 */
struct pairhash {
public:
  template <typename T, typename U>
  std::size_t operator()(const std::pair<T, U> &x) const
  {
    return std::hash<T>()(x.first) ^ std::hash<U>()(x.second);
  }
};

typedef std::unordered_map<std::pair<int,int>, float, pairhash > dok_matrix;

class SeqSparseMatrix
{
private:
	dok_matrix similarity_matrix;
	Aligner * aligner;
	seqan::StringSet<seqan::DnaString> & seqs;
	int num_of_seqs;
	int count; // record the number of pairwise computation

public:
	SeqSparseMatrix(Aligner *aligner_, seqan::StringSet<seqan::DnaString> &seqs_);

	virtual ~SeqSparseMatrix();

	double get(int i, int j);

	void get_submatrix(uvec &rows, uvec &cols, fmat &submatrix);
	void get_submatrix(uword idx, uvec &cols, fvec &submatrix);

	int get_count(){return count;}

	int get_n_rows(){return num_of_seqs;}
};


#endif /* SPARSE_MATRIX_H_ */
