/** 
* @file scaleKernelMatrix.cpp
* @brief scale a kernel matrix
* @author Erik Rodner
* @date 12/21/2009

*/
#include "core/basics/Config.h"
#include "core/vector/MatrixT.h"

using namespace std;
using namespace NICE;


/** 
    
    scale a kernel matrix 
    
*/
int main (int argc, char **argv)
{   
#ifndef __clang__
#ifndef __llvm__
    std::set_terminate(__gnu_cxx::__verbose_terminate_handler);
#endif
#endif

    Config conf ( argc, argv );
    
	string kernel_in = conf.gS("main", "kernel_in");    
	string kernel_out = conf.gS("main", "kernel_out");
    
    Vector labels;
	Matrix kernelMatrix;

	ifstream ifs ( kernel_in.c_str(), ios::in );
	if ( ! ifs.good() )
		fthrow(Exception, "Unable to read kernel matrix from " << kernel_in );

	ifs >> kernelMatrix;
	ifs >> labels;

	ifs.close();

	if ( kernelMatrix.cols() != kernelMatrix.rows() )
	{
		fthrow(Exception, "Kernel matrix is not quadratic!");
	}
	Matrix kernelMatrixScaled ( kernelMatrix.cols(), kernelMatrix.rows() );
    
	for ( uint i = 0 ; i < kernelMatrix.cols(); i++ )
		for ( uint j = 0 ; j < kernelMatrix.rows(); j++ )
		{
			double K_ii = kernelMatrix(i,i);
			double K_jj = kernelMatrix(j,j);
			kernelMatrixScaled(i,j) = kernelMatrix(i,j) / sqrt(K_ii * K_jj);
		}

	ofstream ofs ( kernel_out.c_str(), ios::out );
	if ( ! ofs.good() )
		fthrow(Exception, "Unable to write kernel matrix to " << kernel_out );

	ofs << kernelMatrixScaled;
	ofs << labels;
	ofs.close();
    
    return 0;
}