2
votes

In order to extrcact the coefficients used by the Logistic classifier in Weka, one can use the coefficients methos as axplained here: Can one inspect the weights learned by a logistic regression classifier in weka?.

Yet, not all the attributes given in the data-set (i.e the Instances object) are in use in the classifier.

So my question is- how can I create a mapping of attribute-name\corresponding-coefficient as appears in the toString() method?

for example, using the toString example I get the following coefficient:

enter image description here

I would like to have a mapping as following:

{avgP=-9.6225, BysP=5.3931, Degree=0.0016...}

1

1 Answers

2
votes

The double[][] returned by coefficients() has a different set of attributes than the Instances object you pass into Logistic. I had to peruse the Weka code to understand how to cope with that. I could not find a way to get at the information via methods on Logistic, but you can easily duplicate the Filter it uses and get the same set of attributes to operate with.

I am using Weka as a library in JRuby and thus the code here is Ruby syntax.

import 'weka.filters.unsupervised.attribute.RemoveUseless'


logit_filter = RemoveUseless.new 
logit_filter.setInputFormat train_filtered
logit_filtered = Filter.useFilter(train_filtered, logit_filter)

The logit_filtered variable is an Instances collection that mirrors what is created by Logistic, but there is a final wrinkle. The internals of Logistic keep the Intercept as the first element of the double[][] that is returned with coefficients so we must ignore the first element to map the attribute sets correctly...

java_array = logit.coefficients.to_a #converting java array to ruby
coeffs = java_array.map(&:to_a) #converting second level of java array to ruby

coeffs.each_with_index do |arr, index|
  next if index == 0 #this is the Intercept
  puts "#{logit_filtered.attribute(index-1).name.to_s}: #{coeffs}"
end

This maps things together for me nicely.