1

我正在研究一种使用 Kinect 传感器进行手势识别的解决方案。现在我正在使用 Accord .NET 来训练 HMM。我有一个保存手势的数据集。该数据集有 11 个手势,每个手势有 32 帧,保存了 18 个点。

所以我有一个 (double [12] [32,18]) 输入数据集和一个 (int[12]) 输出数据集,但是当我这样做时:double error = teacher.Run(inputSequences, output),它给了我这个: “指定的参数超出了有效值的范围。”

有谁知道如何解决这个问题?在hmm老师上使用之前应该先处理数据集还是数据集可以这样?

4

2 回答 2

1

I have used Accord.NET in the past and its really one of the best implementations for a HMM engine. However, when I trained my HMM, I passed the HMM parameters (namely PI, A and B) to the Baum Welch Teacher with the input data set supplied using an organized excel sheet. (similar to what Accord's author himself has used in his project). I somehow feel that since you are storing your data set as a multi-dimensional array and directly supplying it to the teacher, its unable to process it properly. Maybe you could supply one gesture record at a time or change the storage structure of your data set altogether. I advice going through the entire example of Accord if you haven't already because it worked just fine for me.

于 2013-04-23T05:51:36.643 回答
0

问题可能是教学算法期望训练序列采用格式double[12][32][18],而不是double[12][32,18]. 训练数据应该是多变量点序列的集合。还应注意,如果您有 11 种可能的手势类别,则int[12]数组中给出的整数标签应仅包含 0 到 10 之间的值。

因此,如果您有 12 个手势样本,每个包含 32 帧,并且每帧是 18 个点的向量,您应该为教师提供一个double[12][32][18]包含观察结果的int[12]数组和一个包含预期类标签的数组。

下面的示例摘自 HiddenMarkovClassifierLearning 文档页面,应该有助于了解向量的组织方式!

// Create a Continuous density Hidden Markov Model Sequence Classifier 
// to detect a multivariate sequence and the same sequence backwards. 

double[][][] sequences = new double[][][]
{
    new double[][] 
    { 
        // This is the first  sequence with label = 0 
        new double[] { 0, 1 },
        new double[] { 1, 2 },
        new double[] { 2, 3 },
        new double[] { 3, 4 },
        new double[] { 4, 5 },
    }, 

    new double[][]
    {
            // This is the second sequence with label = 1 
        new double[] { 4,  3 },
        new double[] { 3,  2 },
        new double[] { 2,  1 },
        new double[] { 1,  0 },
        new double[] { 0, -1 },
    }
};

// Labels for the sequences 
int[] labels = { 0, 1 };

在上面的代码中,我们为 2 个观察序列设置了问题,其中每个序列包含 5 个观察,并且每个观察由 2 个值组成。如您所见,这是一个 double[2][5][2] 数组。类标签数组由 int[2] 给出,仅包含从 0 到 1 的值。

现在,为了使示例更完整,我们可以使用以下代码继续创建和训练模型:

var initialDensity = new MultivariateNormalDistribution(2);

// Creates a sequence classifier containing 2 hidden Markov Models with 2 states 
// and an underlying multivariate mixture of Normal distributions as density. 
var classifier = new HiddenMarkovClassifier<MultivariateNormalDistribution>(
    classes: 2, topology: new Forward(2), initial: initialDensity);

// Configure the learning algorithms to train the sequence classifier 
var teacher = new HiddenMarkovClassifierLearning<MultivariateNormalDistribution>(
    classifier,

    // Train each model until the log-likelihood changes less than 0.0001
    modelIndex => new BaumWelchLearning<MultivariateNormalDistribution>(
        classifier.Models[modelIndex])
    {
        Tolerance = 0.0001,
        Iterations = 0,

        FittingOptions = new NormalOptions()
        {
            Diagonal = true,      // only diagonal covariance matrices
            Regularization = 1e-5 // avoid non-positive definite errors
        }
    }
);

// Train the sequence classifier using the algorithm 
double logLikelihood = teacher.Run(sequences, labels);

现在我们可以测试模型,断言输出类标签确实符合我们的预期:

// Calculate the probability that the given 
//  sequences originated from the model 
double likelihood, likelihood2;

// Try to classify the 1st sequence (output should be 0) 
int c1 = classifier.Compute(sequences[0], out likelihood);

// Try to classify the 2nd sequence (output should be 1) 
int c2 = classifier.Compute(sequences[1], out likelihood2);
于 2014-01-06T11:36:16.920 回答