SHOGUN v0.9.0
|
00001 /* 00002 * This program is free software; you can redistribute it and/or modify 00003 * it under the terms of the GNU General Public License as published by 00004 * the Free Software Foundation; either version 3 of the License, or 00005 * (at your option) any later version. 00006 * 00007 * Written (W) 1999-2010 Soeren Sonnenburg 00008 * Copyright (C) 1999-2009 Fraunhofer Institute FIRST and Max-Planck-Society 00009 * Copyright (C) 2010 Berlin Institute of Technology 00010 */ 00011 00012 #include "lib/common.h" 00013 #include "base/Parameter.h" 00014 #include "kernel/GaussianKernel.h" 00015 #include "features/DotFeatures.h" 00016 #include "lib/io.h" 00017 00018 using namespace shogun; 00019 00020 CGaussianKernel::CGaussianKernel() 00021 : CDotKernel() 00022 { 00023 init(); 00024 } 00025 00026 00027 CGaussianKernel::CGaussianKernel(int32_t size, float64_t w) 00028 : CDotKernel(size) 00029 { 00030 init(); 00031 width=w; 00032 } 00033 00034 CGaussianKernel::CGaussianKernel( 00035 CDotFeatures* l, CDotFeatures* r, float64_t w, int32_t size) 00036 : CDotKernel(size) 00037 { 00038 init(); 00039 width=w; 00040 00041 init(l,r); 00042 } 00043 00044 CGaussianKernel::~CGaussianKernel() 00045 { 00046 cleanup(); 00047 } 00048 00049 void CGaussianKernel::cleanup() 00050 { 00051 if (sq_lhs != sq_rhs) 00052 delete[] sq_rhs; 00053 sq_rhs = NULL; 00054 00055 delete[] sq_lhs; 00056 sq_lhs = NULL; 00057 00058 CKernel::cleanup(); 00059 } 00060 00061 void CGaussianKernel::precompute_squared_helper(float64_t* &buf, CDotFeatures* df) 00062 { 00063 ASSERT(df); 00064 int32_t num_vec=df->get_num_vectors(); 00065 buf=new float64_t[num_vec]; 00066 00067 for (int32_t i=0; i<num_vec; i++) 00068 buf[i]=df->dot(i,df, i); 00069 } 00070 00071 bool CGaussianKernel::init(CFeatures* l, CFeatures* r) 00072 { 00074 cleanup(); 00075 00076 CDotKernel::init(l, r); 00077 precompute_squared(); 00078 return init_normalizer(); 00079 } 00080 00081 float64_t CGaussianKernel::compute(int32_t idx_a, int32_t idx_b) 00082 { 00083 float64_t result=sq_lhs[idx_a]+sq_rhs[idx_b]-2*CDotKernel::compute(idx_a,idx_b); 00084 return exp(-result/width); 00085 } 00086 00087 void CGaussianKernel::load_serializable_post(void) throw (ShogunException) 00088 { 00089 CKernel::load_serializable_post(); 00090 precompute_squared(); 00091 } 00092 00093 void CGaussianKernel::precompute_squared() 00094 { 00095 if (!lhs || !rhs) 00096 return; 00097 00098 precompute_squared_helper(sq_lhs, (CDotFeatures*) lhs); 00099 00100 if (lhs==rhs) 00101 sq_rhs=sq_lhs; 00102 else 00103 precompute_squared_helper(sq_rhs, (CDotFeatures*) rhs); 00104 } 00105 00106 void CGaussianKernel::init() 00107 { 00108 width=1; 00109 sq_lhs=NULL; 00110 sq_rhs=NULL; 00111 m_parameters->add(&width, "width", "Kernel width."); 00112 }