(self,data,classes,featureNames,maxlevel=-1,level=0,forest=0)
The main function, which recursively constructs the tree
The main function, which recursively constructs the tree
The main function which recursively constructs the tree
def make_tree(self,data,classes,featureNames,maxlevel=-1,level=0,forest=0):
		""" The main function, which recursively constructs the tree"""

		nData = len(data)
		nFeatures = len(data[0])
		
		try: 
			self.featureNames
		except:
			self.featureNames = featureNames
			
		# List the possible classes
		newClasses = []
		for aclass in classes:
			if newClasses.count(aclass)==0:
				newClasses.append(aclass)

		# Compute the default class (and total entropy)
		frequency = np.zeros(len(newClasses))

		totalEntropy = 0
		totalGini = 0
		index = 0
		for aclass in newClasses:
			frequency[index] = classes.count(aclass)
			totalEntropy += self.calc_entropy(float(frequency[index])/nData)
			totalGini += (float(frequency[index])/nData)**2

			index += 1

		totalGini = 1 - totalGini
		default = classes[np.argmax(frequency)]

		if nData==0 or nFeatures == 0 or (maxlevel>=0 and level>maxlevel):
			# Have reached an empty branch
			return default
		elif classes.count(classes[0]) == nData:
			# Only 1 class remains
			return classes[0]
		else:

			# Choose which feature is best	
			gain = np.zeros(nFeatures)
			ggain = np.zeros(nFeatures)
			featureSet = range(nFeatures)
			if forest != 0:
				np.random.shuffle(featureSet)
				featureSet = featureSet[0:forest]
			for feature in featureSet:
				g,gg = self.calc_info_gain(data,classes,feature)
				gain[feature] = totalEntropy - g
				ggain[feature] = totalGini - gg

			bestFeature = np.argmax(gain)
			tree = {featureNames[bestFeature]:{}}

			# List the values that bestFeature can take
			values = []
			for datapoint in data:
				if datapoint[feature] not in values:
					values.append(datapoint[bestFeature])

			for value in values:
				# Find the datapoints with each feature value
				newData = []
				newClasses = []
				index = 0
				for datapoint in data:
					if datapoint[bestFeature]==value:
						if bestFeature==0:
							newdatapoint = datapoint[1:]
							newNames = featureNames[1:]
						elif bestFeature==nFeatures:
							newdatapoint = datapoint[:-1]
							newNames = featureNames[:-1]
						else:
							newdatapoint = datapoint[:bestFeature]
							newdatapoint.extend(datapoint[bestFeature+1:])
							newNames = featureNames[:bestFeature]
							newNames.extend(featureNames[bestFeature+1:])
						newData.append(newdatapoint)
						newClasses.append(classes[index])
					index += 1

				# Now recurse to the next level	
				subtree = self.make_tree(newData,newClasses,newNames,maxlevel,level+1,forest)

				# And on returning, add the subtree on to the tree
				tree[featureNames[bestFeature]][value] = subtree

			return tree
def make_tree ( self , data , classes , featureNames , maxlevel = - 1 , level = 0 , forest = 0 ) : nData = len ( data ) nFeatures = len ( data [ 0 ] ) try : self . featureNames except : self . featureNames = featureNames # List the possible classes newClasses = [ ] for aclass in classes : if newClasses . count ( aclass ) == 0 : newClasses . append ( aclass ) # Compute the default class (and total entropy) frequency = np . zeros ( len ( newClasses ) ) totalEntropy = 0 totalGini = 0 index = 0 for aclass in newClasses : frequency [ index ] = classes . count ( aclass ) totalEntropy += self . calc_entropy ( float ( frequency [ index ] ) / nData ) totalGini += ( float ( frequency [ index ] ) / nData ) ** 2 index += 1 totalGini = 1 - totalGini default = classes [ np . argmax ( frequency ) ] if nData == 0 or nFeatures == 0 or ( maxlevel >= 0 and level > maxlevel ) : # Have reached an empty branch return default elif classes . count ( classes [ 0 ] ) == nData : # Only 1 class remains return classes [ 0 ] else : # Choose which feature is best	 gain = np . zeros ( nFeatures ) ggain = np . zeros ( nFeatures ) featureSet = range ( nFeatures ) if forest != 0 : np . random . shuffle ( featureSet ) featureSet = featureSet [ 0 : forest ] for feature in featureSet : g , gg = self . calc_info_gain ( data , classes , feature ) gain [ feature ] = totalEntropy - g ggain [ feature ] = totalGini - gg bestFeature = np . argmax ( gain ) tree = { featureNames [ bestFeature ] : { } } # List the values that bestFeature can take values = [ ] for datapoint in data : if datapoint [ feature ] not in values : values . append ( datapoint [ bestFeature ] ) for value in values : # Find the datapoints with each feature value newData = [ ] newClasses = [ ] index = 0 for datapoint in data : if datapoint [ bestFeature ] == value : if bestFeature == 0 : newdatapoint = datapoint [ 1 : ] newNames = featureNames [ 1 : ] elif bestFeature == nFeatures : newdatapoint = datapoint [ : - 1 ] newNames = featureNames [ : - 1 ] else : newdatapoint = datapoint [ : bestFeature ] newdatapoint . extend ( datapoint [ bestFeature + 1 : ] ) newNames = featureNames [ : bestFeature ] newNames . extend ( featureNames [ bestFeature + 1 : ] ) newData . append ( newdatapoint ) newClasses . append ( classes [ index ] ) index += 1 # Now recurse to the next level	 subtree = self . make_tree ( newData , newClasses , newNames , maxlevel , level + 1 , forest ) # And on returning, add the subtree on to the tree tree [ featureNames [ bestFeature ] ] [ value ] = subtree return tree