39 using namespace shogun;
76 SG_ERROR(
"Kernel still initialized on destruction.\n")
81 SG_INFO(
"Kernel deleted (%p).\n",
this)
105 REQUIRE(l,
"CKernel::init(%p, %p): Left hand side features required!\n", l, r)
106 REQUIRE(r,
"CKernel::init(%p, %p): Right hand side features required!\n", l, r)
135 SG_DEBUG(
"leaving CKernel::init(%p, %p)\n", l, r)
175 SG_ERROR(
"kernel has zero rows: num_lhs=%d num_rhs=%d\n",
178 uint64_t buffer_size=0;
186 if (buffer_size>((uint64_t) totdoc)*totdoc)
187 buffer_size=((uint64_t) totdoc)*totdoc;
198 kernel_cache.active2totdoc = SG_MALLOC(int32_t, totdoc);
199 kernel_cache.totdoc2active = SG_MALLOC(int32_t, totdoc);
209 for(i=0;i<totdoc;i++) {
213 for(i=0;i<totdoc;i++) {
219 for(i=0;i<totdoc;i++) {
228 int32_t docnum, int32_t *active2dnum,
float64_t *buffer,
bool full_line)
234 if (docnum>=num_vectors)
235 docnum=2*num_vectors-1-docnum;
255 for(i=0;(j=active2dnum[i])>=0;i++)
278 for(i=0;(j=active2dnum[i])>=0;i++)
293 register int32_t j,k,l;
303 cache = kernel_cache_clean_and_malloc(m);
311 if((
kernel_cache.index[k] != -1) && (l != -1) && (k != m)) {
325 perror(
"Error: Kernel cache full! => increase cache size");
330 void* CKernel::cache_multiple_kernel_row_helper(
void* p)
333 S_KTHREAD_PARAM* params = (S_KTHREAD_PARAM*) p;
335 for (int32_t i=params->start; i<params->end; i++)
338 int32_t m = params->uncached_rows[i];
339 l=params->kernel_cache->totdoc2active[m];
341 for(j=0;j<params->kernel_cache->activenum;j++)
343 k=params->kernel_cache->active2totdoc[j];
345 if((params->kernel_cache->index[k] != -1) && (l != -1) && (!params->needs_computation[k])) {
346 cache[j]=params->kernel_cache->buffer[((
KERNELCACHE_IDX) params->kernel_cache->activenum)
347 *params->kernel_cache->index[k]+l];
351 if (k>=params->num_vectors)
352 k=2*params->num_vectors-1-k;
354 cache[j]=params->kernel->kernel(m, k);
359 params->needs_computation[m]=0;
373 for(int32_t i=0;i<num_rows;i++)
380 int32_t* uncached_rows = SG_MALLOC(int32_t, num_rows);
382 pthread_t* threads = SG_MALLOC(pthread_t, nthreads-1);
383 S_KTHREAD_PARAM* params = SG_MALLOC(S_KTHREAD_PARAM, nthreads-1);
384 int32_t num_threads=nthreads-1;
387 uint8_t* needs_computation=SG_CALLOC(uint8_t, num_vec);
394 for (int32_t i=0; i<num_rows; i++)
403 needs_computation[idx]=1;
404 uncached_rows[num]=idx;
405 cache[num]= kernel_cache_clean_and_malloc(idx);
408 SG_ERROR(
"Kernel cache full! => increase cache size\n")
423 for (int32_t t=0; t<num_threads; t++)
425 params[t].kernel =
this;
427 params[t].cache = cache;
428 params[t].uncached_rows = uncached_rows;
429 params[t].needs_computation = needs_computation;
430 params[t].num_uncached = num;
431 params[t].start = t*step;
432 params[t].end = (t+1)*step;
436 int code=pthread_create(&threads[t], NULL,
437 CKernel::cache_multiple_kernel_row_helper, (
void*)¶ms[t]);
441 SG_WARNING(
"Thread creation failed (thread %d of %d) "
442 "with error:'%s'\n",t, num_threads, strerror(code));
453 S_KTHREAD_PARAM last_param;
454 last_param.kernel =
this;
456 last_param.cache = cache;
457 last_param.uncached_rows = uncached_rows;
458 last_param.needs_computation = needs_computation;
459 last_param.start = end;
460 last_param.num_uncached = num;
461 last_param.end = num;
464 cache_multiple_kernel_row_helper(&last_param);
467 for (int32_t t=0; t<num_threads; t++)
469 if (pthread_join(threads[t], NULL) != 0)
470 SG_WARNING(
"pthread_join of thread %d/%d failed\n", t, num_threads)
473 SG_FREE(needs_computation);
477 SG_FREE(uncached_rows);
485 int32_t totdoc, int32_t numshrink, int32_t *after)
488 register int32_t i,j,jj,scount;
492 keep=SG_MALLOC(int32_t, totdoc);
493 for(j=0;j<totdoc;j++) {
497 for(jj=0;(jj<
kernel_cache.activenum) && (scount<numshrink);jj++) {
520 for(j=0;j<totdoc;j++) {
521 if((keep[j]) && (
kernel_cache.totdoc2active[j] != -1)) {
568 int32_t CKernel::kernel_cache_malloc()
584 void CKernel::kernel_cache_free(int32_t cacheidx)
592 int32_t CKernel::kernel_cache_free_lru()
594 register int32_t k,least_elem=-1,least_time;
606 if(least_elem != -1) {
607 kernel_cache_free(least_elem);
620 if((result = kernel_cache_malloc()) == -1) {
621 if(kernel_cache_free_lru()) {
622 result = kernel_cache_malloc();
633 #endif //USE_SVMLIGHT
651 SG_DEBUG(
"entering CKernel::remove_lhs_and_rhs\n")
664 #endif //USE_SVMLIGHT
665 SG_DEBUG(
"leaving CKernel::remove_lhs_and_rhs\n")
678 #endif //USE_SVMLIGHT
692 #endif //USE_SVMLIGHT
695 #define ENUM_CASE(n) case n: SG_INFO(#n " ") break;
702 "SLOWBUTMEMEFFICIENT");
815 int32_t count, int32_t *IDX,
float64_t * weights)
817 SG_ERROR(
"kernel does not support linadd optimization\n")
823 SG_ERROR(
"kernel does not support linadd optimization\n")
829 SG_ERROR(
"kernel does not support linadd optimization\n")
834 int32_t num_vec, int32_t* vec_idx,
float64_t* target, int32_t num_suppvec,
837 SG_ERROR(
"kernel does not support batch computation\n")
842 SG_ERROR(
"kernel does not support linadd optimization, add_to_normal not implemented\n")
847 SG_ERROR(
"kernel does not support linadd optimization, clear_normal not implemented\n")
856 int32_t vector_idx,
float64_t * subkernel_contrib)
858 SG_ERROR(
"kernel compute_by_subkernel not implemented\n")
878 SG_ERROR(
"number of subkernel weights should be one ...\n")
888 REQUIRE(casted,
"CKernel::obtain_from_generic(): Error, provided object"
889 " of class \"%s\" is not a subclass of CKernel!\n",
900 int32_t* sv_idx=SG_MALLOC(int32_t, num_suppvec);
903 for (int32_t i=0; i<num_suppvec; i++)
947 SG_ADD(&
num_lhs,
"num_lhs",
"Number of feature vectors on left hand side.",
949 SG_ADD(&
num_rhs,
"num_rhs",
"Number of feature vectors on right hand side.",
980 #endif //USE_SVMLIGHT
1021 "Invalid block begin index (%d, %d)!\n", block_begin, block_begin)
1023 "Invalid block size (%d) at starting index (%d, %d)! "
1024 "Please use smaller blocks!", block_size, block_begin, block_begin)
1025 REQUIRE(block_size>=1,
"Invalid block size (%d)!\n", block_size)
1032 #pragma omp parallel for
1033 for (
index_t i=0; i<block_size; ++i)
1037 for (
index_t j=i+1; j<block_size; ++j)
1052 #pragma omp parallel for
1053 for (
index_t i=0; i<block_size; ++i)
1073 block_begin_col>=0 && block_begin_col<
num_rhs,
1074 "Invalid block begin index (%d, %d)!\n",
1075 block_begin_row, block_begin_col)
1077 block_begin_col+block_size_col<=
num_rhs,
1078 "Invalid block size (%d, %d) at starting index (%d, %d)! "
1079 "Please use smaller blocks!", block_size_row, block_size_col,
1080 block_begin_row, block_begin_col)
1081 REQUIRE(block_size_row>=1 && block_size_col>=1,
1082 "Invalid block size (%d, %d)!\n", block_size_row, block_size_col)
1085 if (no_diag && block_size_row!=block_size_col)
1087 SG_WARNING(
"Not removing the main diagonal since block is not square!\n");
1094 #pragma omp parallel for
1095 for (
index_t i=0; i<block_size_row; ++i)
1098 for (
index_t j=0; j<block_size_col; ++j)
1101 kernel(i+block_begin_row, j+block_begin_col);
1113 index_t block_size,
bool no_diag)
1120 "Invalid block begin index (%d, %d)!\n", block_begin, block_begin)
1122 "Invalid block size (%d) at starting index (%d, %d)! "
1123 "Please use smaller blocks!", block_size, block_begin, block_begin)
1124 REQUIRE(block_size>=1,
"Invalid block size (%d)!\n", block_size)
1133 #pragma omp parallel for
1134 for (
index_t i=0; i<block_size; ++i)
1138 for (
index_t j=i+1; j<block_size; ++j)
1141 #pragma omp critical
1153 #pragma omp parallel for
1154 for (
index_t i=0; i<block_size; ++i)
1167 block_begin,
index_t block_size,
bool no_diag)
1174 "Invalid block begin index (%d, %d)!\n", block_begin, block_begin)
1176 "Invalid block size (%d) at starting index (%d, %d)! "
1177 "Please use smaller blocks!", block_size, block_begin, block_begin)
1178 REQUIRE(block_size>=1,
"Invalid block size (%d)!\n", block_size)
1189 #pragma omp parallel for
1190 for (
index_t i=0; i<block_size; ++i)
1194 for (
index_t j=i+1; j<block_size; ++j)
1197 #pragma omp critical
1211 #pragma omp parallel for
1212 for (
index_t i=0; i<block_size; ++i)
1215 row_sum(i, 0)+=diag;
1216 row_sum(i, 1)+=diag*diag;
1227 index_t block_size_col,
bool no_diag)
1233 block_begin_col>=0 && block_begin_col<
num_rhs,
1234 "Invalid block begin index (%d, %d)!\n",
1235 block_begin_row, block_begin_col)
1237 block_begin_col+block_size_col<=
num_rhs,
1238 "Invalid block size (%d, %d) at starting index (%d, %d)! "
1239 "Please use smaller blocks!", block_size_row, block_size_col,
1240 block_begin_row, block_begin_col)
1241 REQUIRE(block_size_row>=1 && block_size_col>=1,
1242 "Invalid block size (%d, %d)!\n", block_size_row, block_size_col)
1245 if (no_diag && block_size_row!=block_size_col)
1247 SG_WARNING(
"Not removing the main diagonal since block is not square!\n");
1258 #pragma omp parallel for
1259 for (
index_t i=0; i<block_size_row; ++i)
1262 for (
index_t j=0; j<block_size_col; ++j)
1265 kernel(i+block_begin_row, j+block_begin_col);
1266 #pragma omp critical
1269 sum[j+block_size_row]+=k;
1282 int32_t i_start=params->
start;
1283 int32_t i_end=params->
end;
1285 T* result=params->
result;
1287 int32_t n=params->
n;
1288 int32_t m=params->
m;
1292 int64_t total=total_start;
1294 for (int32_t i=i_start; i<i_end; i++)
1301 for (int32_t j=j_start; j<n; j++)
1306 if (symmetric && i!=j)
1313 if (symmetric && i!=j)
1339 int64_t total_num = int64_t(m)*n;
1342 bool symmetric= (
lhs &&
lhs==
rhs && m==n);
1344 SG_DEBUG(
"returning kernel matrix of size %dx%d\n", m, n)
1346 result=SG_MALLOC(T, total_num);
1349 if (num_threads < 2)
1362 get_kernel_matrix_helper<T>((
void*) ¶ms);
1366 pthread_t* threads = SG_MALLOC(pthread_t, num_threads-1);
1368 int64_t step= total_num/num_threads;
1373 for (t=0; t<num_threads; t++)
1376 params[t].
result = result;
1386 int code=pthread_create(&threads[t], NULL,
1387 CKernel::get_kernel_matrix_helper<T>, (
void*)¶ms[t]);
1391 SG_WARNING(
"Thread creation failed (thread %d of %d) "
1392 "with error:'%s'\n",t, num_threads, strerror(code));
1399 params[t].
result = result;
1408 get_kernel_matrix_helper<T>(¶ms[t]);
1410 for (t=0; t<num_threads; t++)
1412 if (pthread_join(threads[t], NULL) != 0)
1413 SG_WARNING(
"pthread_join of thread %d/%d failed\n", t, num_threads)
1429 template void* CKernel::get_kernel_matrix_helper<float64_t>(
void* p);
1430 template void* CKernel::get_kernel_matrix_helper<float32_t>(
void* p);
virtual void clear_normal()
virtual const char * get_name() const =0
virtual void load_serializable_post()
virtual bool init(CFeatures *lhs, CFeatures *rhs)
int32_t get_num_support_vectors()
int32_t compute_row_start(int64_t offs, int32_t n, bool symmetric)
virtual void set_matrix(const bool *matrix, int32_t num_feat, int32_t num_vec)
virtual void compute_by_subkernel(int32_t vector_idx, float64_t *subkernel_contrib)
void cache_multiple_kernel_rows(int32_t *key, int32_t varnum)
int32_t get_num_threads() const
int32_t num_rhs
number of feature vectors on right hand side
static void * get_kernel_matrix_helper(void *p)
Class ShogunException defines an exception which is thrown whenever an error inside of shogun occurs...
virtual bool set_normalizer(CKernelNormalizer *normalizer)
virtual float64_t sum_block(index_t block_begin_row, index_t block_begin_col, index_t block_size_row, index_t block_size_col, bool no_diag=false)
virtual int32_t get_num_vectors() const =0
virtual void save_serializable_pre()
virtual bool delete_optimization()
int32_t kernel_cache_space_available()
float64_t kernel(int32_t idx_a, int32_t idx_b)
virtual void remove_rhs()
takes all necessary steps if the rhs is removed from kernel
virtual int32_t get_num_vec_lhs()
SGMatrix< float64_t > get_kernel_matrix()
int32_t cache_size
cache_size in MB
void kernel_cache_shrink(int32_t totdoc, int32_t num_shrink, int32_t *after)
bool get_is_initialized()
virtual SGMatrix< float64_t > row_wise_sum_squared_sum_symmetric_block(index_t block_begin, index_t block_size, bool no_diag=true)
float64_t combined_kernel_weight
virtual void register_params()
virtual void remove_lhs_and_rhs()
virtual CKernelNormalizer * get_normalizer()
Class SGObject is the base class of all shogun objects.
virtual SGVector< float64_t > row_col_wise_sum_block(index_t block_begin_row, index_t block_begin_col, index_t block_size_row, index_t block_size_col, bool no_diag=false)
void cache_kernel_row(int32_t x)
#define SG_OBJ_PROGRESS(o,...)
virtual float64_t sum_symmetric_block(index_t block_begin, index_t block_size, bool no_diag=true)
virtual SGVector< float64_t > get_subkernel_weights()
KERNEL_CACHE kernel_cache
kernel cache
virtual EFeatureType get_feature_type()=0
KERNELCACHE_ELEM * kernel_matrix
A File access base class.
virtual void save_serializable_post()
virtual float64_t compute_optimized(int32_t vector_idx)
EOptimizationType get_optimization_type()
virtual void save_serializable_post()
float64_t get_alpha(int32_t idx)
float64_t get_combined_kernel_weight()
virtual SGVector< float64_t > row_wise_sum_symmetric_block(index_t block_begin, index_t block_size, bool no_diag=true)
virtual EFeatureClass get_feature_class() const =0
Identity Kernel Normalization, i.e. no normalization is applied.
int32_t num_lhs
number of feature vectors on left hand side
The class Kernel Normalizer defines a function to post-process kernel values.
int32_t get_support_vector(int32_t idx)
static bool cancel_computations()
virtual int32_t get_num_vec_rhs()
virtual void set_subkernel_weights(SGVector< float64_t > weights)
void set_const(T const_elem)
virtual bool init_normalizer()
bool optimization_initialized
EOptimizationType opt_type
virtual void load_serializable_post()
CFeatures * rhs
feature vectors to occur on right hand side
static CKernel * obtain_from_generic(CSGObject *kernel)
virtual bool init(CKernel *k)=0
virtual void compute_batch(int32_t num_vec, int32_t *vec_idx, float64_t *target, int32_t num_suppvec, int32_t *IDX, float64_t *alphas, float64_t factor=1.0)
virtual EKernelType get_kernel_type()=0
virtual bool init_optimization(int32_t count, int32_t *IDX, float64_t *weights)
CFeatures * lhs
feature vectors to occur on left hand side
The class Features is the base class of all feature objects.
virtual void save_serializable_pre()
void kernel_cache_cleanup()
virtual void remove_lhs()
int32_t kernel_cache_check(int32_t cacheidx)
virtual int32_t get_num_subkernels()
bool init_optimization_svm(CSVM *svm)
A generic Support Vector Machine Interface.
void kernel_cache_reset_lru()
CKernelNormalizer * normalizer
virtual SGVector< float64_t > get_kernel_row(int32_t i)
void set_const(T const_elem)
virtual bool has_features()
void kernel_cache_init(int32_t size, bool regression_hack=false)
virtual void add_to_normal(int32_t vector_idx, float64_t weight)
float64_t KERNELCACHE_ELEM
void resize_kernel_cache(KERNELCACHE_IDX size, bool regression_hack=false)
virtual EFeatureType get_feature_type() const =0
virtual EFeatureClass get_feature_class()=0