Hide keyboard shortcuts

Hot-keys on this page

r m x p   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

98

99

100

101

102

103

104

105

106

107

108

109

110

111

112

113

114

115

116

117

118

119

120

""" 

Mathematical computation are done in this module. Those involve mostly 

geometry, and predefined grids shapes 

""" 

import numpy as np 

import pandas as pd 

 

 

def mode_moves_supported(): 

return { 

'on_cubic_grid': { 

'param': 

['grid_spacing'], 

'describe': 

"Agent restricted to move on a grid"}, 

'free_run': { 

'param': [], 

'describe': 

"Freely moving agent, pos(t+dt)=pos+speed (dt=1)"}} 

 

 

def next_pos(motion_vec, move_mode, move_param=None): 

"""return the future position knowing speed and current position 

 

:param motion_vec: the position and speed of the agent 

(pandas Series with columns ['x','y','z','dx','dy','dz']) 

:param grid_spacing: the spacing between two grid points 

(only relevant for regular grids) 

:param grid_mode: the type of grid. 

 

..todo: add literal include for supported_grid_mode 

""" 

if isinstance(motion_vec, pd.Series) is False: 

raise TypeError('motion vector must be a pandas Series') 

if move_mode not in mode_moves_supported().keys(): 

raise KeyError( 

'move mode must is not supported {}'.format(move_mode)) 

tuples = [('location', 'dx'), ('location', 'dy'), 

('location', 'dz')] 

index = pd.MultiIndex.from_tuples(tuples, 

names=['position', 

'orientation']) 

speed = pd.Series(index=index) 

speed.loc[('location', 'dx')] = motion_vec[('location', 'dx')] 

speed.loc[('location', 'dy')] = motion_vec[('location', 'dy')] 

speed.loc[('location', 'dz')] = motion_vec[('location', 'dz')] 

# speed = motion_vec.loc[['dx', 'dy', 'dz']] 

if move_mode == 'on_cubic_grid': 

# speed in spherical coord 

epsilon = np.arctan2(speed['location']['dz'], 

np.sqrt(speed['location']['dx']**2 + 

speed['location']['dy']**2)) 

phi = np.arctan2(speed['location']['dy'], speed['location']['dx']) 

radius = np.sqrt(np.sum(speed**2)) 

if np.isclose(radius, 0): 

# scaling = 0 

speed = 0 * speed 

else: 

tuples = [('location', 'dx'), ('location', 'dy'), 

('location', 'dz')] 

index = pd.MultiIndex.from_tuples(tuples, 

names=['position', 

'orientation']) 

deltas = pd.Series(index=index) 

deltas['location']['dz'] = float(epsilon > (np.pi / 8) - 

epsilon < (np.pi / 8)) 

edgecases = np.linspace(-np.pi, np.pi, 9) 

case_i = np.argmin(np.abs(phi - edgecases)) 

if case_i == 8 or case_i == 0 or case_i == 1 or case_i == 7: 

deltas['location']['dx'] = -1 

elif case_i == 3 or case_i == 4 or case_i == 5: 

deltas['location']['dx'] = 1 

else: 

deltas['location']['dx'] = 0 

 

if case_i == 1 or case_i == 2 or case_i == 3: 

deltas['location']['dy'] = -1 

elif case_i == 5 or case_i == 6 or case_i == 7: 

deltas['location']['dy'] = 1 

 

else: 

deltas['location']['dy'] = 0 

# scaling = 1 

speed = move_param['grid_spacing'] * deltas 

elif move_mode is 'free_run': 

pass 

# scaling = 1 # <=> dt = 1, user need to scale speed in dt units 

else: 

raise ValueError('grid_mode is not supported') 

toreturn = motion_vec.copy() 

toreturn.loc[('location', 'x')] += speed['location']['dx'] 

toreturn.loc[('location', 'y')] += speed['location']['dy'] 

toreturn.loc[('location', 'z')] += speed['location']['dz'] 

return toreturn 

 

 

def closest_pos(pos, positions): 

"""Return the closest position from a list of positions 

 

:param pos: the position to find (a pandas Series with ['x','y','z'] 

:param positions: the possible closest positions 

(a pandas dataframe with 

[['location','x'],['location','y'],['location','z']]) 

""" 

 

euclidian_dist = np.sqrt( 

(pos['location']['x'] - positions['location']['x'])**2 

+ (pos['location']['y'] - positions['location']['y'])**2 

+ (pos['location']['z'] - positions['location']['z'])**2) 

return positions.loc[euclidian_dist.idxmin()] 

 

 

def closest_pos_memory_friendly(pos, database): 

"""Return the closest position from a list of positions 

 

:param pos: the position to find (a pandas Series with ['x','y','z'] 

:param database: the possible closest positions 

(a pandas dataframe with ['x','y','z']) 

""" 

raise NameError('Not implemated')