/**
* Copyright (C) 2013-2017 Vasilis Vryniotis
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.datumbox.framework.core.machinelearning.classification;
import com.datumbox.framework.common.Configuration;
import com.datumbox.framework.common.concurrency.ForkJoinStream;
import com.datumbox.framework.common.concurrency.StreamMethods;
import com.datumbox.framework.common.dataobjects.AssociativeArray;
import com.datumbox.framework.core.common.dataobjects.Dataframe;
import com.datumbox.framework.core.common.dataobjects.Record;
import com.datumbox.framework.common.dataobjects.TypeInference;
import com.datumbox.framework.common.storage.interfaces.BigMap;
import com.datumbox.framework.common.storage.interfaces.StorageEngine;
import com.datumbox.framework.common.storage.interfaces.StorageEngine.MapType;
import com.datumbox.framework.common.storage.interfaces.StorageEngine.StorageHint;
import com.datumbox.framework.core.machinelearning.common.abstracts.AbstractTrainer;
import com.datumbox.framework.core.machinelearning.common.abstracts.modelers.AbstractClassifier;
import com.datumbox.framework.core.machinelearning.common.interfaces.PredictParallelizable;
import com.datumbox.framework.core.machinelearning.common.interfaces.TrainParallelizable;
import com.datumbox.framework.core.statistics.descriptivestatistics.Descriptives;
import com.datumbox.framework.core.mathematics.regularization.ElasticNetRegularizer;
import com.datumbox.framework.core.mathematics.regularization.L1Regularizer;
import com.datumbox.framework.core.mathematics.regularization.L2Regularizer;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.Set;
/**
* The SoftMaxRegression implements the Multinomial Logistic Regression classifier.
*
* References:
* http://blog.datumbox.com/machine-learning-tutorial-the-multinomial-logistic-regression-softmax-regression/
* http://blog.datumbox.com/tuning-the-learning-rate-in-gradient-descent/
* http://www.cs.cmu.edu/afs/cs/user/aberger/www/html/tutorial/node3.html
* http://acl.ldc.upenn.edu/P/P02/P02-1002.pdf
* http://www.aclweb.org/anthology/P09-1054
*
* @author Vasilis Vryniotis
*/
public class SoftMaxRegression extends AbstractClassifier implements PredictParallelizable, TrainParallelizable {
/** {@inheritDoc} */
public static class ModelParameters extends AbstractClassifier.AbstractModelParameters {
private static final long serialVersionUID = 1L;
@BigMap(keyClass=List.class, valueClass=Double.class, mapType=MapType.HASHMAP, storageHint=StorageHint.IN_MEMORY, concurrent=true)
private Map, Double> thitas; //the thita parameters of the model
/**
* @param storageEngine
* @see AbstractTrainer.AbstractModelParameters#AbstractModelParameters(StorageEngine)
*/
protected ModelParameters(StorageEngine storageEngine) {
super(storageEngine);
}
/**
* Getter for the Thita coefficients of the model.
*
* @return
*/
public Map, Double> getThitas() {
return thitas;
}
/**
* Setter for the Thita coefficients of the model.
*
* @param thitas
*/
protected void setThitas(Map, Double> thitas) {
this.thitas = thitas;
}
}
/** {@inheritDoc} */
public static class TrainingParameters extends AbstractClassifier.AbstractTrainingParameters {
private static final long serialVersionUID = 1L;
private int totalIterations=100;
private double learningRate=0.1;
private double l1=0.0;
private double l2=0.0;
/**
* Getter for the total iterations of the training process.
*
* @return
*/
public int getTotalIterations() {
return totalIterations;
}
/**
* Setter for the total iterations of the training process.
*
* @param totalIterations
*/
public void setTotalIterations(int totalIterations) {
this.totalIterations = totalIterations;
}
/**
* Getter for the initial value of the Learning Rate.
*
* @return
*/
public double getLearningRate() {
return learningRate;
}
/**
* Setter for the initial value of the Learning Rate. This value will be
* adapted during the iterations.
*
* @param learningRate
*/
public void setLearningRate(double learningRate) {
this.learningRate = learningRate;
}
/**
* Getter for the value of L1 regularization.
*
* @return
*/
public double getL1() {
return l1;
}
/**
* Setter for the value of the L1 regularization.
*
* @param l1
*/
public void setL1(double l1) {
this.l1 = l1;
}
/**
* Getter for the value of L2 regularization.
*
* @return
*/
public double getL2() {
return l2;
}
/**
* Setter for the value of the L2 regularization.
*
* @param l2
*/
public void setL2(double l2) {
this.l2 = l2;
}
}
/**
* @param trainingParameters
* @param configuration
* @see AbstractTrainer#AbstractTrainer(AbstractTrainingParameters, Configuration)
*/
protected SoftMaxRegression(TrainingParameters trainingParameters, Configuration configuration) {
super(trainingParameters, configuration);
streamExecutor = new ForkJoinStream(knowledgeBase.getConfiguration().getConcurrencyConfiguration());
}
/**
* @param storageName
* @param configuration
* @see AbstractTrainer#AbstractTrainer(String, Configuration)
*/
protected SoftMaxRegression(String storageName, Configuration configuration) {
super(storageName, configuration);
streamExecutor = new ForkJoinStream(knowledgeBase.getConfiguration().getConcurrencyConfiguration());
}
private boolean parallelized = true;
/**
* This executor is used for the parallel processing of streams with custom
* Thread pool.
*/
protected final ForkJoinStream streamExecutor;
/** {@inheritDoc} */
@Override
public boolean isParallelized() {
return parallelized;
}
/** {@inheritDoc} */
@Override
public void setParallelized(boolean parallelized) {
this.parallelized = parallelized;
}
/** {@inheritDoc} */
@Override
protected void _predict(Dataframe newData) {
_predictDatasetParallel(newData, knowledgeBase.getStorageEngine(), knowledgeBase.getConfiguration().getConcurrencyConfiguration());
}
/** {@inheritDoc} */
@Override
public Prediction _predictRecord(Record r) {
ModelParameters modelParameters = knowledgeBase.getModelParameters();
Set
Ads help maintain this website.