]> granicus.if.org Git - liblinear/commitdiff
.
authorYu-Chin <guestwalk@gmail.com>
Fri, 25 Oct 2013 15:22:32 +0000 (23:22 +0800)
committerYu-Chin <guestwalk@gmail.com>
Fri, 25 Oct 2013 15:22:32 +0000 (23:22 +0800)
Makefile
linear.cpp
predict.c
train.c

index 7a74e26af9a377205258e49a256e9aebbe970908..166308be6fde53fe142276f11f2499b06545b29c 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -1,6 +1,6 @@
 CXX ?= g++
 CC ?= gcc
-CFLAGS = -Wall -Wconversion -O3 -fPIC
+CFLAGS = -Wall -Wconversion -O3 -fPIC -fopenmp
 LIBS = blas/blas.a
 SHVER = 1
 OS = $(shell uname)
index ca835ff7a7e4f11183d01229dac4d150c5deff6a..b7e1c8846e63a1871ec39b4d7603167dd38c36ea 100644 (file)
@@ -4,6 +4,8 @@
 #include <string.h>
 #include <stdarg.h>
 #include <locale.h>
+#include <unistd.h>
+#include <time.h>
 #include "linear.h"
 #include "tron.h"
 typedef signed char schar;
@@ -44,6 +46,8 @@ static void info(const char *fmt,...)
 static void info(const char *fmt,...) {}
 #endif
 
+extern int nr_threads;
+
 class l2r_lr_fun: public function
 {
 public:
@@ -64,6 +68,8 @@ private:
        double *z;
        double *D;
        const problem *prob;
+    double **XTv_sub;
+       double *wa;
 };
 
 l2r_lr_fun::l2r_lr_fun(const problem *prob, double *C)
@@ -75,12 +81,19 @@ l2r_lr_fun::l2r_lr_fun(const problem *prob, double *C)
        z = new double[l];
        D = new double[l];
        this->C = C;
+
+    XTv_sub = new double*[nr_threads];
+    for(int ti=0;ti<nr_threads;ti++)
+        XTv_sub[ti] = new double[prob->n];
+
+    wa = new double[l];
 }
 
 l2r_lr_fun::~l2r_lr_fun()
 {
        delete[] z;
        delete[] D;
+    delete[] wa;
 }
 
 
@@ -97,6 +110,7 @@ double l2r_lr_fun::fun(double *w)
        for(i=0;i<w_size;i++)
                f += w[i]*w[i];
        f /= 2.0;
+//#pragma omp parallel for  private(i) reduction(+:f)
        for(i=0;i<l;i++)
        {
                double yz = y[i]*z[i];
@@ -116,6 +130,7 @@ void l2r_lr_fun::grad(double *w, double *g)
        int l=prob->l;
        int w_size=get_nr_variable();
 
+//#pragma omp parallel for private(i)
        for(i=0;i<l;i++)
        {
                z[i] = 1/(1 + exp(-y[i]*z[i]));
@@ -138,24 +153,31 @@ void l2r_lr_fun::Hv(double *s, double *Hs)
        int i;
        int l=prob->l;
        int w_size=get_nr_variable();
-       double *wa = new double[l];
+
+    for(i=0; i<l; ++i)
+        wa[i] = 0;
 
        Xv(s, wa);
+//#pragma omp parallel for private(i)
        for(i=0;i<l;i++)
                wa[i] = C[i]*D[i]*wa[i];
 
        XTv(wa, Hs);
+//#pragma omp parallel for private(i)
        for(i=0;i<w_size;i++)
                Hs[i] = s[i] + Hs[i];
-       delete[] wa;
 }
 
 void l2r_lr_fun::Xv(double *v, double *Xv)
 {
+    time_t start,end;
+    time(&start);
+
        int i;
        int l=prob->l;
        feature_node **x=prob->x;
 
+#pragma omp parallel for private(i)
        for(i=0;i<l;i++)
        {
                feature_node *s=x[i];
@@ -166,26 +188,45 @@ void l2r_lr_fun::Xv(double *v, double *Xv)
                        s++;
                }
        }
+
+    time(&end);
+    double diff = difftime(end,start);
+    //printf("Xv time: %.2lf\n",diff);
 }
 
 void l2r_lr_fun::XTv(double *v, double *XTv)
 {
+    time_t start,end;
+    time(&start);
+
        int i;
        int l=prob->l;
        int w_size=get_nr_variable();
        feature_node **x=prob->x;
 
+    for(int ti=0;ti<nr_threads;ti++)
+        for(i=0;i<w_size;i++)
+            XTv_sub[ti][i]=0;
        for(i=0;i<w_size;i++)
                XTv[i]=0;
-       for(i=0;i<l;i++)
-       {
-               feature_node *s=x[i];
-               while(s->index!=-1)
-               {
-                       XTv[s->index-1]+=v[i]*s->value;
-                       s++;
-               }
-       }
+#pragma omp parallel for private(i)
+    for(int ti=0; ti<nr_threads; ti++) 
+        for(i=ti*(l/nr_threads);i<(ti+1)*(l/nr_threads);i++)
+        {
+            feature_node *s=x[i];
+            while(s->index!=-1)
+            {
+                XTv_sub[ti][s->index-1]+=v[i]*s->value;
+                s++;
+            }
+        }
+    for(int ti=0; ti<nr_threads; ti++) 
+        for(i=0;i<w_size;i++)
+            XTv[i] += XTv_sub[ti][i];
+
+    time(&end);
+    double diff = difftime(end,start);
+    //printf("XTv time: %.2lf\n",diff);
 }
 
 class l2r_l2_svc_fun: public function
index c5b3f1d56ee0883a387ab721d0d98aa0e254473f..c110dbc119b750687ab0e0372a45ac9c9d86d326 100644 (file)
--- a/predict.c
+++ b/predict.c
@@ -11,6 +11,7 @@ static int (*info)(const char *fmt,...) = &printf;
 
 struct feature_node *x;
 int max_nr_attr = 64;
+int nr_threads;
 
 struct model* model_;
 int flag_predict_probability=0;
diff --git a/train.c b/train.c
index d3881757eaea96268b75cd079a97a94806e4123e..aa493b5b82bb083c0b876fce3030d51058ea5b70 100644 (file)
--- a/train.c
+++ b/train.c
@@ -4,6 +4,9 @@
 #include <string.h>
 #include <ctype.h>
 #include <errno.h>
+#include <unistd.h>
+#include <time.h>
+#include <omp.h>
 #include "linear.h"
 #define Malloc(type,n) (type *)malloc((n)*sizeof(type))
 #define INF HUGE_VAL
@@ -92,6 +95,7 @@ struct model* model_;
 int flag_cross_validation;
 int nr_fold;
 double bias;
+int nr_threads;
 
 int main(int argc, char **argv)
 {
@@ -115,7 +119,12 @@ int main(int argc, char **argv)
        }
        else
        {
+        time_t start,end;
+        time(&start);
                model_=train(&prob, &param);
+        time(&end);
+        double diff = difftime(end,start);
+        printf("training time: %.2lf\n",diff);
                if(save_model(model_file_name, model_))
                {
                        fprintf(stderr,"can't save model to file %s\n",model_file_name);
@@ -188,6 +197,7 @@ void parse_command_line(int argc, char **argv, char *input_file_name, char *mode
        param.weight = NULL;
        flag_cross_validation = 0;
        bias = -1;
+    nr_threads = 2;
 
        // parse options
        for(i=1;i<argc;i++)
@@ -238,6 +248,11 @@ void parse_command_line(int argc, char **argv, char *input_file_name, char *mode
                        case 'q':
                                print_func = &print_null;
                                i--;
+
+                       case 't':
+                               nr_threads = atoi(argv[i]);
+                               break;
+
                                break;
 
                        default: