[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [pygame] Numeric optimization advice



John Eikenberry wrote:
>             # spread the influence
>             # diamond_h
>             neighbors = _shift_up(weightmap)/factor
>             neighbors += _shift_left(weightmap)/factor
>             neighbors += _shift_right(weightmap)/factor
>             neighbors += _shift_down(weightmap)/factor
>             neighbors += _shift_hex_up(weightmap)/factor
>             neighbors += _shift_hex_down(weightmap)/factor

this is certainly the core of your work. the first thing you could easily 
do is remove all the "/factor" and add a final line "neighbors /= factor" 
or perhaps slightly better might be "neighbors *= (1/factor)"

the other thing would be the absolute rediculous number of calls that must 
be going to _shift_up and _shift_down.

def shift_up(cells):
     return concatenate((cells[1:], cells[-1:]*edge_mod))

this looks pretty rough to me. the "concantenate" cannot make a 'clean 
reference' of the array, so it must make a copy of all the data. the 
*edge_mod must also make a copy of the last column.

i'm actually a little confused what  the edge_mod is for exactly. is it 
really needed? the edge_mod will require we make a copy of something, here 
is a potential quicker plan? i'm also a little confused here since the 
passed in "hex_map" is unused, and all the action only takes place on the 
arrays of "zeros".



class InfluenceMap:
	def __init__(self, hex_map):
		self.hex_map = hex_map
		self.temp_map = zeros(hex_map.size, Float16)
		self.temp_up = self.temp_map[2:,1:1]
		self.temp_down = self.temp_map[:-2,1:1]
		self.temp_left = self.temp_map[1:1,2:]
		self.temp_right = self.temp_map[1:1,:-2]
		self.temp_hexup = self.temp_map[2:,2:]
		self.temp_hexdown = self.temp_map[:-2,:-2]
			

	def step(self, iterations):
		edge_mod = 0.66
		centermap = self.hex_map[1:1,1:1]
		for x in range(iterations):
			self.temp_map[:] = self.hex_map
			self.temp_map[1] *= edge_mod
			self.temp_map[-1] *= edge_mod
			self.temp_map[:,1] *= edge_mod
			self.temp_map[:,-1] *= edge_mod
			centermap = self.temp_up
			centermap += self.temp_down
                         centermap += self.temp_left
			centermap += self.temp_right
			centermap += self.temp_hexup
			centermap += self.temp_hexdown
			centermap *= 1.0 / 6.0


now, using my quick email logic, the "hexup" and "hexdown" logic may be 
incorrect. if so you'll get best results by working on the even/odd rows 
each at a time, instead of like your shift_hex_up function that makes a 
copy of the entire array.

there should also be no need for clamping the results from 'overheated' 
values here? since we are averaging all the surrounding cells, no value can 
become 'hotter' than any of its neighbors.

anyways, beware my code here. i just typed it into the email program, and 
it may not work, or worse, muhaha


____________________________________
pygame mailing list
pygame-users@seul.org
http://pygame.seul.org