def forward(self, *args): assert len(args) == 2 assert isinstance(args[0], Tensor) assert isinstance(args[1], Tensor) self.A = args[0] self.B = args[1] assert self.shape == self.B.data.shape C_data = self.A.data set_sub_ndarray(C_data, self.B.data, self.coordinate_tuple) assert C_data.shape == self.A.data.shape C = Tensor(C_data) C.left_child = self.A C.right_child = self.B self.output_shape = C_data.shape C.grad_fn = self self.A.parent = C self.B.parent = C if self.A.requires_grad or self.B.requires_grad: C.requires_grad = True return C
def forward(self, *args, **kwargs): assert len(args) == 1 assert isinstance(args[0], Tensor) assert isinstance(args[0].data, np.ndarray) self.A = args[0] self.shape = self.A.data.shape C_data = self.A.data.reshape(self.target_shape) C = Tensor() C.data = C_data C.left_child = self.A # C.right_child = self.B C.grad_fn = self self.A.parent = C #self.B.parent = C if self.A.requires_grad: C.requires_grad = True return C
def forward(self, *args): assert len(args) == 2 assert isinstance(args[0], Tensor) assert isinstance(args[1], Tensor) self.A = args[0] self.B = args[1] # Currrently, A is the batch samples assert self.A.data.shape[1:] == self.B.data.shape C = Tensor(self.A.data * self.B.data) # In numpy, * means element-wise multiply C.name = self.name C.grad_fn = self if self.A.requires_grad or self.B.requires_grad: C.requires_grad = True self.A.parent = C self.B.parent = C C.left_child = self.A C.right_child = self.B return C
def forward(self, *args): assert len(args) == 2 assert isinstance(args[0], Tensor) assert isinstance(args[1], Tensor) self.A = args[0] self.B = args[1] # May not have the same shape, use broadcast instead. # assert self.A.data.shape == self.B.data.shape if not isinstance(self.A.data, np.ndarray): C = Tensor(self.B.data) elif not isinstance(self.B.data, np.ndarray): C = Tensor(self.A.data) else: C = Tensor(self.A.data + self.B.data) C.name = self.name C.grad_fn = self if self.A.requires_grad or self.B.requires_grad: C.requires_grad = True self.A.parent = C self.B.parent = C C.left_child = self.A C.right_child = self.B self.output_shape = C.data.shape return C
def forward(self, *args): assert len(args) == 1 assert isinstance(args[0], Tensor) self.A = args[0] C_data = np.sum(self.A.data, axis=self.axis) if isinstance(self.target_shape, tuple): C_data = C_data.reshape(self.target_shape) self.output_shape = C_data.shape C = Tensor(C_data) C.name = self.name C.grad_fn = self if self.A.requires_grad: C.requires_grad = True self.A.parent = C # self.B.parent = C C.left_child = self.A #C.right_child = self.B return C
def forward(self, *args): assert len(args) == 2 assert isinstance(args[0], Tensor) assert isinstance(args[1], Tensor) self.A = args[0] # Y self.B = args[1] # Y_pred assert self.A.data.shape == self.B.data.shape # loss = .5 * ((Y_pred - Y) ** 2) / n_samples n_samples = self.A.data.shape[0] loss_value = 0.5 * (np.sum((self.B.data - self.A.data) ** 2))\ / n_samples C = Tensor(loss_value) C.name = self.name C.grad_fn = self # A = Y is the label, which is constant. self.A.requires_grad = False # B = Y_pred if self.B.requires_grad: C.requires_grad = True self.A.parent = C self.B.parent = C C.left_child = self.A C.right_child = self.B return C
def forward(self, *args): """ # Input X: [n_samples, width, height] (Padded Size) width_idx, height_idx, kernel_size, stride # Output Y_pred: [n_samples, K, K], kernel_size * kernel_size Y_pred = X[:, W_i*S:W_i*S+K, H_i*S:H_i*S+K] Y_pred = X [:, width_idx * stride : width_idx * stride + kernel_size, height_idx * stride : height_idx * stride + kernel_size] """ assert len(args) == 1 assert isinstance(args[0], Tensor) assert isinstance(args[0].data, np.ndarray) assert len(args[0].data.shape) == 3 X = args[0] self.X = X # 1.Save input tensors for current function Y_pred_data = self.X.data[:, self.width_idx * self.stride:self.width_idx * self.stride + self.kernel_size, self.height_idx * self.stride:self.height_idx * self.stride + self.kernel_size] Y_pred = Tensor(Y_pred_data) Y_pred.grad_fn = self # 3. Set grad_fn & requires_grad for current function if self.X.requires_grad: Y_pred.requires_grad = True Y_pred.left_child = X # 4. Set parent-child relationships. X.parent = Y_pred return Y_pred # 2. Return new Tensor
def forward(self, *args): assert len(args) == 1 assert isinstance(args[0], Tensor) self.A = args[0] # Sigmoid: f(x) = sigmoid(x) C = Tensor(sigmoid(self.A.data)) C.name = self.name C.grad_fn = self if self.A.requires_grad: C.requires_grad = True self.A.parent = C C.left_child = self.A self.C = C return C
def forward(self, *args): assert len(args) == 1 assert isinstance(args[0], Tensor) assert self.repeat_time > 0 self.A = args[0] C_data = np.repeat(self.A.data, self.repeat_time) if self.target_shape: C_data = C_data.reshape(self.target_shape) C = Tensor(C_data) C.grad_fn = self C.left_child = self.A self.A.parent = C self.output_shape = C_data.shape if self.A.requires_grad: C.requires_grad = True return C
def forward(self, *args): """ # Input X: [n_samples, width, height] # Output Y_pred: [n_samples, width + 2P, height + 2P] """ assert len(args) == 1 assert isinstance(args[0], Tensor) assert isinstance(args[0].data, np.ndarray) assert len(args[0].data.shape) == 3 n_samples, width, height = args[0].data.shape self.n_samples = n_samples X = args[0] self.X = X # 1.Save input tensors for current function P = self.padding # !!! Do Zero Padding Here Y_pred_data = np.zeros((self.n_samples, width + 2 * P, height + 2 * P)) # Copy X.data into Y, leave paddings in the around. if P == 0: Y_pred_data = X.data else: Y_pred_data[:, P:-P, P:-P] = X.data Y_pred = Tensor(Y_pred_data) Y_pred.grad_fn = self # 3. Set grad_fn & requires_grad for current function if self.X.requires_grad: Y_pred.requires_grad = True Y_pred.left_child = X # 4. Set parent-child relationships. X.parent = Y_pred return Y_pred # 2. Return new Tensor
def forward(self, *args): assert len(args) == 1 assert isinstance(args[0], Tensor) self.A = args[0] # ReLU: f(x) = max(0, x) # For numpy, relu(x) = x * (x > 0), relu_grad(x) = 1 * (x > 0) #C = Tensor(np.clip(self.A.data, a_min=0, a_max=np.Infinity)) C = Tensor(self.A.data * (self.A.data > 0)) C.name = self.name C.grad_fn = self if self.A.requires_grad: C.requires_grad = True self.A.parent = C C.left_child = self.A return C
def forward(self, *args): assert len(args) == 2 assert isinstance(args[0], Tensor) assert isinstance(args[1], Tensor) self.A = args[0] self.B = args[1] assert self.A.data.shape == self.B.data.shape C = Tensor(self.A.data - self.B.data) C.name = self.name C.grad_fn = self if self.A.requires_grad or self.B.requires_grad: C.requires_grad = True self.A.parent = C self.B.parent = C C.left_child = self.A C.right_child = self.B return C
def forward(self, *args): assert len(args) == 1 assert isinstance(args[0], Tensor) self.A = args[0] C_data = get_sub_ndarray(self.A.data, self.coordinate_tuple) C = Tensor() C.data = C_data C.left_child = self.A # C.right_child = self.B C.grad_fn = self self.A.parent = C #self.B.parent = C if self.A.requires_grad: C.requires_grad = True return C