source: orange/Orange/OrangeWidgets/Data/OWContinuize.py @ 11776:f6a6d74a9dc2

Revision 11776:f6a6d74a9dc2, 8.2 KB checked in by Ales Erjavec <ales.erjavec@…>, 5 months ago (diff)

Fixed class treatment in Continuize widget.

(fixes #1347)

Line 
1import Orange
2from OWWidget import *
3from orngWrap import PreprocessedLearner
4import OWGUI
5
6NAME = "Continuize"
7DESCRIPTION = """Turns discrete features into continuous.
8Can also normalize existing continuous features."""
9ICON = "icons/Continuize.svg"
10PRIORITY = 2110
11CATEGORY = "Data"
12MAINTAINER = "Janez Demsar"
13MAINTAINER_EMAIL = "janez.demsar(@at@)fri.uni-lj.si"
14INPUTS = [("Data", Orange.data.Table, "setData")]
15OUTPUTS = [("Data", Orange.data.Table, ),
16           ("Preprocessor", PreprocessedLearner, )]
17
18class OWContinuize(OWWidget):
19    settingsList = ["multinomialTreatment", "classTreatment", "zeroBased", "continuousTreatment", "autosend"]
20    contextHandlers = {"": ClassValuesContextHandler("", ["targetValue"])}
21
22    multinomialTreats = (("Target or First value as base", orange.DomainContinuizer.LowestIsBase),
23                         ("Most frequent value as base", orange.DomainContinuizer.FrequentIsBase),
24                         ("One attribute per value", orange.DomainContinuizer.NValues),
25                         ("Ignore multinomial attributes", orange.DomainContinuizer.Ignore),
26                         ("Ignore all discrete attributes", orange.DomainContinuizer.IgnoreAllDiscrete),
27                         ("Treat as ordinal", orange.DomainContinuizer.AsOrdinal),
28                         ("Divide by number of values", orange.DomainContinuizer.AsNormalizedOrdinal))
29
30    continuousTreats = (("Leave them as they are", orange.DomainContinuizer.Leave),
31                        ("Normalize by span", orange.DomainContinuizer.NormalizeBySpan),
32                        ("Normalize by variance", orange.DomainContinuizer.NormalizeByVariance))
33
34    classTreats = (("Leave it as it is", orange.DomainContinuizer.Ignore),
35                   ("Treat as ordinal", orange.DomainContinuizer.AsOrdinal),
36                   ("Divide by number of values", orange.DomainContinuizer.AsNormalizedOrdinal),
37                   ("Specified target value", -1))
38   
39    valueRanges = ["from -1 to 1", "from 0 to 1"]
40
41    def __init__(self,parent=None, signalManager = None, name = "Continuizer"):
42        OWWidget.__init__(self, parent, signalManager, name, wantMainArea = 0)
43
44        self.inputs = [("Data", ExampleTable, self.setData)]
45        self.outputs = [("Data", ExampleTable), ("Preprocessor", PreprocessedLearner)]
46
47        self.multinomialTreatment = 0
48        self.targetValue = 0
49        self.continuousTreatment = 0
50        self.classTreatment = 0
51        self.zeroBased = 1
52        self.autosend = 0
53        self.dataChanged = False
54        self.loadSettings()
55
56        bgMultiTreatment = OWGUI.widgetBox(self.controlArea, "Multinomial attributes")
57        OWGUI.radioButtonsInBox(bgMultiTreatment, self, "multinomialTreatment", btnLabels=[x[0] for x in self.multinomialTreats], callback=self.sendDataIf)
58
59        self.controlArea.layout().addSpacing(4)
60
61        bgMultiTreatment = OWGUI.widgetBox(self.controlArea, "Continuous attributes")
62        OWGUI.radioButtonsInBox(bgMultiTreatment, self, "continuousTreatment", btnLabels=[x[0] for x in self.continuousTreats], callback=self.sendDataIf)
63
64        self.controlArea.layout().addSpacing(4)
65
66        bgClassTreatment = OWGUI.widgetBox(self.controlArea, "Discrete class attribute")
67        self.ctreat = OWGUI.radioButtonsInBox(bgClassTreatment, self, "classTreatment", btnLabels=[x[0] for x in self.classTreats], callback=self.sendDataIf)
68#        hbox = OWGUI.widgetBox(bgClassTreatment, orientation = "horizontal")
69#        OWGUI.separator(hbox, 19, 4)
70        hbox = OWGUI.indentedBox(bgClassTreatment, sep=OWGUI.checkButtonOffsetHint(self.ctreat.buttons[-1]), orientation="horizontal")
71        self.cbTargetValue = OWGUI.comboBox(hbox, self, "targetValue", label="Target Value ", items=[], orientation="horizontal", callback=self.cbTargetSelected)
72        def setEnabled(*args):
73            self.cbTargetValue.setEnabled(self.classTreatment == 3)
74        self.connect(self.ctreat.group, SIGNAL("buttonClicked(int)"), setEnabled)
75        setEnabled() 
76
77        self.controlArea.layout().addSpacing(4)
78
79        zbbox = OWGUI.widgetBox(self.controlArea, "Value range")
80        OWGUI.radioButtonsInBox(zbbox, self, "zeroBased", btnLabels=self.valueRanges, callback=self.sendDataIf)
81
82        self.controlArea.layout().addSpacing(4)
83
84        snbox = OWGUI.widgetBox(self.controlArea, "Send data")
85        OWGUI.button(snbox, self, "Send data", callback=self.sendData, default=True)
86        OWGUI.checkBox(snbox, self, "autosend", "Send automatically", callback=self.enableAuto)
87        self.data = None
88        self.sendPreprocessor()
89        self.resize(150,300)
90        #self.adjustSize()
91
92    def cbTargetSelected(self):
93        self.classTreatment = 3
94        self.sendDataIf()
95
96    def setData(self,data):
97        self.closeContext()
98
99        if not data:
100            self.data = None
101            self.cbTargetValue.clear()
102            self.openContext("", self.data)
103            self.send("Data", None)
104        else:
105            if not self.data or data.domain.classVar != self.data.domain.classVar:
106                self.cbTargetValue.clear()
107                if data.domain.classVar and data.domain.classVar.varType == orange.VarTypes.Discrete:
108                    for v in data.domain.classVar.values:
109                        self.cbTargetValue.addItem(" "+v)
110                    self.ctreat.setDisabled(False)
111                    self.targetValue = 0
112                else:
113                    self.ctreat.setDisabled(True)
114            self.data = data
115            self.openContext("", self.data)
116            self.sendData()
117
118    def sendDataIf(self):
119        self.dataChanged = True
120        if self.autosend:
121            self.sendPreprocessor()
122            self.sendData()
123
124    def enableAuto(self):
125        if self.dataChanged:
126            self.sendPreprocessor()
127            self.sendData()
128
129    def constructContinuizer(self):
130        conzer = orange.DomainContinuizer()
131        conzer.zeroBased = self.zeroBased
132        conzer.continuousTreatment = self.continuousTreatment
133        conzer.multinomialTreatment = self.multinomialTreats[self.multinomialTreatment][1]
134        conzer.classTreatment = self.classTreats[self.classTreatment][1]
135        return conzer
136
137    def sendPreprocessor(self):
138        continuizer = self.constructContinuizer()
139        self.send("Preprocessor", PreprocessedLearner(
140            lambda data, weightId=0, tc=(self.targetValue if self.classTreatment == 3 else -1): \
141                orange.ExampleTable(continuizer(data, weightId, tc) if data.domain.classVar and self.data.domain.classVar.varType == orange.VarTypes.Discrete else \
142                                    continuizer(data, weightId), data)))
143               
144               
145    def sendData(self):
146        continuizer = self.constructContinuizer()
147        if self.data:
148            if self.data.domain.classVar and self.data.domain.classVar.varType == orange.VarTypes.Discrete:
149                domain = continuizer(self.data, 0, self.targetValue if self.classTreatment == 3 else -1)
150            else:
151                domain = continuizer(self.data, 0)
152            domain.addmetas(self.data.domain.getmetas())
153            self.send("Data", orange.ExampleTable(domain, self.data))
154        self.dataChanged = False
155       
156    def sendReport(self):
157        self.reportData(self.data, "Input data")
158        clstr = "None"
159        if self.data is not None:
160            classVar = self.data.domain.classVar
161            if self.classTreatment == 3 and classVar and classVar.varType == orange.VarTypes.Discrete and len(classVar.values) >= 2: 
162                clstr = "Dummy variable for target '%s'" % classVar.values[self.targetValue]
163            else:
164                clstr = self.classTreats[self.classTreatment][0]
165        self.reportSettings("Settings",
166                            [("Multinominal attributes", self.multinomialTreats[self.multinomialTreatment][0]),
167                             ("Continuous attributes", self.continuousTreats[self.continuousTreatment][0]),
168                             ("Class attribute", clstr),
169                             ("Value range", self.valueRanges[self.zeroBased])])
170
171if __name__ == "__main__":
172    a = QApplication(sys.argv)
173    ow = OWContinuize()
174    data = Orange.data.Table("iris.tab")
175    ow.setData(data)
176    ow.show()
177    a.exec_()
178    ow.saveSettings()
Note: See TracBrowser for help on using the repository browser.