import math class Vector3: def __init__(self,x,y,z): self.x=x self.y=y self.z=z def __add__(self,v): return Vector3(self.x+v.x, self.y+v.y, self.z+v.z) def __iadd__(self,v): self.x+=v.x self.y+=v.y self.z+=v.z return self def __sub__(self,v): return Vector3(self.x-v.x, self.y-v.y, self.z-v.z) def __isub__(self,v): self.x-=v.x self.y-=v.y self.z-=v.z return self def __neg__(self): return Vector3(-self.x, -self.y, -self.z) def __mul__(self,a): # scalar or dot product if isinstance(a,Vector3): return self.x*a.x + self.y*a.y + self.z*a.z else: return Vector3(self.x*a, self.y*a, self.z*a) def __imul__(self,a): if isinstance(a,Vector3): raise BadOperandError(self,a,'attempted in-place dot multiplication') self.x*=a self.y*=a self.z*=a return self def __rmul__(self,a): return self.__mul__(a) def __truediv__(self,a): return Vector3(self.x/a, self.y/a, self.z/a) def __itruediv__(self,a): self.x/=a self.y/=a self.z/=a return self def __floordiv__(self,a): return Vector3(self.x//a, self.y//a, self.z//a) def __ifloordiv__(self,a): self.x//=a self.y//=a self.z//=a return self def __xor__(self,v): # vector cross product return Vector3(self.y*v.z-self.z*v.y, self.z*v.x-self.x*v.z, self.x*v.y-self.y*v.x) def __ixor__(self,v): (self.x, self.y, self.z)=(self.y*v.z-self.z*v.y, self.z*v.x-self.x*v.z, self.x*v.y-self.y*v.x) return self def __abs__(self): return math.sqrt(self.x*self.x + self.y*self.y + self.z*self.z) ## Multiplicates the vector as to set the first nonzero coordinate to 1. def canonize(self): if self.x!=0: factor=self.x elif self.y!=0: factor=self.y elif self.z!=0: factor=self.z else: factor=1 self/=factor return self def __str__(self): return str((self.x,self.y,self.z)) def __repr__(self): return 'Vector3'+self.__str__() class BadOperandError(ArithmeticError): def __init__(self,u,v,message): self.u=u self.v=v self.message=message