public static svm_model svm_load_model(StreamReader reader) { var savedCulture = Thread.CurrentThread.CurrentCulture; Thread.CurrentThread.CurrentCulture = CultureInfo.InvariantCulture; // read parameters svm_model model = new svm_model(); svm_parameter param = new svm_parameter(); model.param = param; model.rho = null; model.probA = null; model.probB = null; model.label = null; model.nSV = null; while (true) { String cmd = reader.ReadLine(); String arg = cmd.Substring(cmd.IndexOf(' ') + 1); if (cmd.StartsWith("svm_type")) { int i; for (i = 0; i < svm_type_table.Length; i++) { if (arg.IndexOf(svm_type_table[i], StringComparison.InvariantCultureIgnoreCase) != -1) { param.svm_type = i; break; } } if (i == svm_type_table.Length) { Console.Error.WriteLine("unknown svm type."); return null; } } else if (cmd.StartsWith("kernel_type")) { int i; for (i = 0; i < kernel_type_table.Length; i++) { if (arg.IndexOf(kernel_type_table[i], StringComparison.InvariantCultureIgnoreCase) != -1) { param.kernel_type = i; break; } } if (i == kernel_type_table.Length) { Console.Error.WriteLine("unknown kernel function."); return null; } } else if (cmd.StartsWith("degree")) param.degree = atoi(arg); else if (cmd.StartsWith("gamma")) param.gamma = atof(arg); else if (cmd.StartsWith("coef0")) param.coef0 = atof(arg); else if (cmd.StartsWith("nr_class")) model.nr_class = atoi(arg); else if (cmd.StartsWith("total_sv")) model.l = atoi(arg); else if (cmd.StartsWith("rho")) { int n = model.nr_class * (model.nr_class - 1) / 2; model.rho = new double[n]; var st = arg.Split(' ', '\t', '\n', '\r', '\f'); for (int i = 0; i < n; i++) model.rho[i] = atof(st[i]); } else if (cmd.StartsWith("label")) { int n = model.nr_class; model.label = new int[n]; var st = arg.Split(' ', '\t', '\n', '\r', '\f'); for (int i = 0; i < n; i++) model.label[i] = atoi(st[i]); } else if (cmd.StartsWith("probA")) { int n = model.nr_class * (model.nr_class - 1) / 2; model.probA = new double[n]; var st = arg.Split(' ', '\t', '\n', '\r', '\f'); for (int i = 0; i < n; i++) model.probA[i] = atof(st[i]); } else if (cmd.StartsWith("probB")) { int n = model.nr_class * (model.nr_class - 1) / 2; model.probB = new double[n]; var st = arg.Split(' ', '\t', '\n', '\r', '\f'); for (int i = 0; i < n; i++) model.probB[i] = atof(st[i]); } else if (cmd.StartsWith("nr_sv")) { int n = model.nr_class; model.nSV = new int[n]; var st = arg.Split(' ', '\t', '\n', '\r', '\f'); for (int i = 0; i < n; i++) model.nSV[i] = atoi(st[i]); } else if (cmd.StartsWith("SV")) { break; } else { Console.Error.WriteLine("unknown text in model file: [" + cmd + "]"); return null; } } // read sv_coef and SV int m = model.nr_class - 1; int l = model.l; model.sv_coef = new double[m][]; for (int k = 0; k < m; k++) model.sv_coef[k] = new double[l]; model.SV = new svm_node[l][]; for (int i = 0; i < l; i++) { String line = reader.ReadLine(); var st = line.Split(' ', '\t', '\n', '\r', '\f', ':'); for (int k = 0; k < m; k++) { model.sv_coef[k][i] = atof(st[k]); } // skip y value st = st.Skip(1).ToArray(); int n = st.Length / 2; model.SV[i] = new svm_node[n]; for (int j = 0; j < n; j++) { model.SV[i][j] = new svm_node(); model.SV[i][j].index = atoi(st[2 * j]); model.SV[i][j].value = atof(st[2 * j + 1]); } } Thread.CurrentThread.CurrentCulture = savedCulture; return model; }
public static int svm_check_probability_model(svm_model model) { if (((model.param.svm_type == svm_parameter.C_SVC || model.param.svm_type == svm_parameter.NU_SVC) && model.probA != null && model.probB != null) || ((model.param.svm_type == svm_parameter.EPSILON_SVR || model.param.svm_type == svm_parameter.NU_SVR) && model.probA != null)) return 1; else return 0; }
public static void svm_save_model(string model_file_name, svm_model model) { //DataOutputStream fp = new DataOutputStream(new BufferedOutputStream(new FileOutputStream(model_file_name))); var writer = new StreamWriter(model_file_name); svm_save_model(writer, model); }
public static void svm_save_model(StreamWriter writer, svm_model model) { var savedCulture = Thread.CurrentThread.CurrentCulture; Thread.CurrentThread.CurrentCulture = CultureInfo.InvariantCulture; svm_parameter param = model.param; writer.Write("svm_type " + svm_type_table[param.svm_type] + Environment.NewLine); writer.Write("kernel_type " + kernel_type_table[param.kernel_type] + Environment.NewLine); if (param.kernel_type == svm_parameter.POLY) writer.Write("degree " + param.degree + Environment.NewLine); if (param.kernel_type == svm_parameter.POLY || param.kernel_type == svm_parameter.RBF || param.kernel_type == svm_parameter.SIGMOID) writer.Write("gamma " + param.gamma.ToString("r") + Environment.NewLine); if (param.kernel_type == svm_parameter.POLY || param.kernel_type == svm_parameter.SIGMOID) writer.Write("coef0 " + param.coef0.ToString("r") + Environment.NewLine); int nr_class = model.nr_class; int l = model.l; writer.Write("nr_class " + nr_class + Environment.NewLine); writer.Write("total_sv " + l + Environment.NewLine); { writer.Write("rho"); for (int i = 0; i < nr_class * (nr_class - 1) / 2; i++) writer.Write(" " + model.rho[i].ToString("r")); writer.Write(Environment.NewLine); } if (model.label != null) { writer.Write("label"); for (int i = 0; i < nr_class; i++) writer.Write(" " + model.label[i]); writer.Write(Environment.NewLine); } if (model.probA != null) // regression has probA only { writer.Write("probA"); for (int i = 0; i < nr_class * (nr_class - 1) / 2; i++) writer.Write(" " + model.probA[i].ToString("r")); writer.Write(Environment.NewLine); } if (model.probB != null) { writer.Write("probB"); for (int i = 0; i < nr_class * (nr_class - 1) / 2; i++) writer.Write(" " + model.probB[i].ToString("r")); writer.Write(Environment.NewLine); } if (model.nSV != null) { writer.Write("nr_sv"); for (int i = 0; i < nr_class; i++) writer.Write(" " + model.nSV[i]); writer.Write(Environment.NewLine); } writer.WriteLine("SV"); double[][] sv_coef = model.sv_coef; svm_node[][] SV = model.SV; for (int i = 0; i < l; i++) { for (int j = 0; j < nr_class - 1; j++) writer.Write(sv_coef[j][i].ToString("r") + " "); svm_node[] p = SV[i]; if (param.kernel_type == svm_parameter.PRECOMPUTED) writer.Write("0:" + (int)(p[0].value)); else for (int j = 0; j < p.Length; j++) writer.Write(p[j].index + ":" + p[j].value.ToString("r") + " "); writer.Write(Environment.NewLine); } writer.Flush(); Thread.CurrentThread.CurrentCulture = savedCulture; }
public static double svm_predict(svm_model model, svm_node[] x) { int nr_class = model.nr_class; double[] dec_values; if (model.param.svm_type == svm_parameter.ONE_CLASS || model.param.svm_type == svm_parameter.EPSILON_SVR || model.param.svm_type == svm_parameter.NU_SVR) dec_values = new double[1]; else dec_values = new double[nr_class * (nr_class - 1) / 2]; double pred_result = svm_predict_values(model, x, dec_values); return pred_result; }
public static double svm_predict_probability(svm_model model, svm_node[] x, double[] prob_estimates) { if ((model.param.svm_type == svm_parameter.C_SVC || model.param.svm_type == svm_parameter.NU_SVC) && model.probA != null && model.probB != null) { int i; int nr_class = model.nr_class; double[] dec_values = new double[nr_class * (nr_class - 1) / 2]; svm_predict_values(model, x, dec_values); double min_prob = 1e-7; double[][] pairwise_prob = new double[nr_class][]; int k = 0; for (i = 0; i < nr_class; i++) pairwise_prob[i] = new double[nr_class]; for (int j = i + 1; j < nr_class; j++) { pairwise_prob[i][j] = Math.Min(Math.Max(sigmoid_predict(dec_values[k], model.probA[k], model.probB[k]), min_prob), 1 - min_prob); pairwise_prob[j][i] = 1 - pairwise_prob[i][j]; k++; } multiclass_probability(nr_class, pairwise_prob, prob_estimates); int prob_max_idx = 0; for (i = 1; i < nr_class; i++) if (prob_estimates[i] > prob_estimates[prob_max_idx]) prob_max_idx = i; return model.label[prob_max_idx]; } else return svm_predict(model, x); }
public static double svm_get_svr_probability(svm_model model) { if ((model.param.svm_type == svm_parameter.EPSILON_SVR || model.param.svm_type == svm_parameter.NU_SVR) && model.probA != null) return model.probA[0]; else { Console.Error.WriteLine("Model doesn't contain information for SVR probability inference"); return 0; } }
public static double svm_predict_values(svm_model model, svm_node[] x, double[] dec_values) { int i; if (model.param.svm_type == svm_parameter.ONE_CLASS || model.param.svm_type == svm_parameter.EPSILON_SVR || model.param.svm_type == svm_parameter.NU_SVR) { double[] sv_coef = model.sv_coef[0]; double sum = 0; for (i = 0; i < model.l; i++) sum += sv_coef[i] * Kernel.k_function(x, model.SV[i], model.param); sum -= model.rho[0]; dec_values[0] = sum; if (model.param.svm_type == svm_parameter.ONE_CLASS) return (sum > 0) ? 1 : -1; else return sum; } else { int nr_class = model.nr_class; int l = model.l; double[] kvalue = new double[l]; for (i = 0; i < l; i++) kvalue[i] = Kernel.k_function(x, model.SV[i], model.param); int[] start = new int[nr_class]; start[0] = 0; for (i = 1; i < nr_class; i++) start[i] = start[i - 1] + model.nSV[i - 1]; int[] vote = new int[nr_class]; for (i = 0; i < nr_class; i++) vote[i] = 0; int p = 0; for (i = 0; i < nr_class; i++) for (int j = i + 1; j < nr_class; j++) { double sum = 0; int si = start[i]; int sj = start[j]; int ci = model.nSV[i]; int cj = model.nSV[j]; int k; double[] coef1 = model.sv_coef[j - 1]; double[] coef2 = model.sv_coef[i]; for (k = 0; k < ci; k++) sum += coef1[si + k] * kvalue[si + k]; for (k = 0; k < cj; k++) sum += coef2[sj + k] * kvalue[sj + k]; sum -= model.rho[p]; dec_values[p] = sum; if (dec_values[p] > 0) ++vote[i]; else ++vote[j]; p++; } int vote_max_idx = 0; for (i = 1; i < nr_class; i++) if (vote[i] > vote[vote_max_idx]) vote_max_idx = i; return model.label[vote_max_idx]; } }
public static int svm_get_nr_class(svm_model model) { return model.nr_class; }
public static void svm_get_labels(svm_model model, int[] label) { if (model.label != null) for (int i = 0; i < model.nr_class; i++) label[i] = model.label[i]; }
public static int svm_get_svm_type(svm_model model) { return model.param.svm_type; }
// // Interface functions // public static svm_model svm_train(svm_problem prob, svm_parameter param) { svm_model model = new svm_model(); model.param = param; if (param.svm_type == svm_parameter.ONE_CLASS || param.svm_type == svm_parameter.EPSILON_SVR || param.svm_type == svm_parameter.NU_SVR) { // regression or one-class-svm model.nr_class = 2; model.label = null; model.nSV = null; model.probA = null; model.probB = null; model.sv_coef = new double[1][]; if (param.probability == 1 && (param.svm_type == svm_parameter.EPSILON_SVR || param.svm_type == svm_parameter.NU_SVR)) { model.probA = new double[1]; model.probA[0] = svm_svr_probability(prob, param); } decision_function f = svm_train_one(prob, param, 0, 0); model.rho = new double[1]; model.rho[0] = f.rho; int nSV = 0; int i; for (i = 0; i < prob.l; i++) if (Math.Abs(f.alpha[i]) > 0) ++nSV; model.l = nSV; model.SV = new svm_node[nSV][]; model.sv_coef[0] = new double[nSV]; int j = 0; for (i = 0; i < prob.l; i++) if (Math.Abs(f.alpha[i]) > 0) { model.SV[j] = prob.x[i]; model.sv_coef[0][j] = f.alpha[i]; ++j; } } else { // classification int l = prob.l; int[] tmp_nr_class = new int[1]; int[][] tmp_label = new int[1][]; int[][] tmp_start = new int[1][]; int[][] tmp_count = new int[1][]; int[] perm = new int[l]; // group training data of the same class svm_group_classes(prob, tmp_nr_class, tmp_label, tmp_start, tmp_count, perm); int nr_class = tmp_nr_class[0]; int[] label = tmp_label[0]; int[] start = tmp_start[0]; int[] count = tmp_count[0]; if (nr_class == 1) svm.info("WARNING: training data in only one class. See README for details." + Environment.NewLine); svm_node[][] x = new svm_node[l][]; int i; for (i = 0; i < l; i++) x[i] = prob.x[perm[i]]; // calculate weighted C double[] weighted_C = new double[nr_class]; for (i = 0; i < nr_class; i++) weighted_C[i] = param.C; for (i = 0; i < param.nr_weight; i++) { int j; for (j = 0; j < nr_class; j++) if (param.weight_label[i] == label[j]) break; if (j == nr_class) Console.Error.WriteLine("WARNING: class label " + param.weight_label[i] + " specified in weight is not found"); else weighted_C[j] *= param.weight[i]; } // train k*(k-1)/2 models bool[] nonzero = new bool[l]; for (i = 0; i < l; i++) nonzero[i] = false; decision_function[] f = new decision_function[nr_class * (nr_class - 1) / 2]; double[] probA = null, probB = null; if (param.probability == 1) { probA = new double[nr_class * (nr_class - 1) / 2]; probB = new double[nr_class * (nr_class - 1) / 2]; } int p = 0; for (i = 0; i < nr_class; i++) for (int j = i + 1; j < nr_class; j++) { svm_problem sub_prob = new svm_problem(); int si = start[i], sj = start[j]; int ci = count[i], cj = count[j]; sub_prob.l = ci + cj; sub_prob.x = new svm_node[sub_prob.l][]; sub_prob.y = new double[sub_prob.l]; int k; for (k = 0; k < ci; k++) { sub_prob.x[k] = x[si + k]; sub_prob.y[k] = +1; } for (k = 0; k < cj; k++) { sub_prob.x[ci + k] = x[sj + k]; sub_prob.y[ci + k] = -1; } if (param.probability == 1) { double[] probAB = new double[2]; svm_binary_svc_probability(sub_prob, param, weighted_C[i], weighted_C[j], probAB); probA[p] = probAB[0]; probB[p] = probAB[1]; } f[p] = svm_train_one(sub_prob, param, weighted_C[i], weighted_C[j]); for (k = 0; k < ci; k++) if (!nonzero[si + k] && Math.Abs(f[p].alpha[k]) > 0) nonzero[si + k] = true; for (k = 0; k < cj; k++) if (!nonzero[sj + k] && Math.Abs(f[p].alpha[ci + k]) > 0) nonzero[sj + k] = true; ++p; } // build output model.nr_class = nr_class; model.label = new int[nr_class]; for (i = 0; i < nr_class; i++) model.label[i] = label[i]; model.rho = new double[nr_class * (nr_class - 1) / 2]; for (i = 0; i < nr_class * (nr_class - 1) / 2; i++) model.rho[i] = f[i].rho; if (param.probability == 1) { model.probA = new double[nr_class * (nr_class - 1) / 2]; model.probB = new double[nr_class * (nr_class - 1) / 2]; for (i = 0; i < nr_class * (nr_class - 1) / 2; i++) { model.probA[i] = probA[i]; model.probB[i] = probB[i]; } } else { model.probA = null; model.probB = null; } int nnz = 0; int[] nz_count = new int[nr_class]; model.nSV = new int[nr_class]; for (i = 0; i < nr_class; i++) { int nSV = 0; for (int j = 0; j < count[i]; j++) if (nonzero[start[i] + j]) { ++nSV; ++nnz; } model.nSV[i] = nSV; nz_count[i] = nSV; } svm.info("Total nSV = " + nnz + Environment.NewLine); model.l = nnz; model.SV = new svm_node[nnz][]; p = 0; for (i = 0; i < l; i++) if (nonzero[i]) model.SV[p++] = x[i]; int[] nz_start = new int[nr_class]; nz_start[0] = 0; for (i = 1; i < nr_class; i++) nz_start[i] = nz_start[i - 1] + nz_count[i - 1]; model.sv_coef = new double[nr_class - 1][]; for (i = 0; i < nr_class - 1; i++) model.sv_coef[i] = new double[nnz]; p = 0; for (i = 0; i < nr_class; i++) for (int j = i + 1; j < nr_class; j++) { // classifier (i,j): coefficients with // i are in sv_coef[j-1][nz_start[i]...], // j are in sv_coef[i][nz_start[j]...] int si = start[i]; int sj = start[j]; int ci = count[i]; int cj = count[j]; int q = nz_start[i]; int k; for (k = 0; k < ci; k++) if (nonzero[si + k]) model.sv_coef[j - 1][q++] = f[p].alpha[k]; q = nz_start[j]; for (k = 0; k < cj; k++) if (nonzero[sj + k]) model.sv_coef[i][q++] = f[p].alpha[ci + k]; ++p; } } return model; }
private SupportVectorMachineModel(SupportVectorMachineModel original, Cloner cloner) : base(original, cloner) { // only using a shallow copy here! (gkronber) this.model = original.model; this.rangeTransform = original.rangeTransform; this.allowedInputVariables = (string[])original.allowedInputVariables.Clone(); if (original.classValues != null) this.classValues = (double[])original.classValues.Clone(); }
public SupportVectorMachineModel(svm_model model, RangeTransform rangeTransform, string targetVariable, IEnumerable<string> allowedInputVariables) : base(targetVariable) { this.name = ItemName; this.description = ItemDescription; this.model = model; this.rangeTransform = rangeTransform; this.allowedInputVariables = allowedInputVariables.ToArray(); }
public SupportVectorMachineModel(svm_model model, RangeTransform rangeTransform, string targetVariable, IEnumerable<string> allowedInputVariables, IEnumerable<double> classValues) : this(model, rangeTransform, targetVariable, allowedInputVariables) { this.classValues = classValues.ToArray(); }