def predict(node_info: MixtureGaussianParams, pvals: List[Union[str, float]]) -> Optional[float]: """ Func to get prediction from current node node_info: nodes info from distributions pvals: parent values Return value from MixtureGaussian node """ mean = node_info["mean"] covariance = node_info["covars"] w = node_info["coef"] n_comp = len(node_info['coef']) if n_comp != 0: if pvals: indexes = [i for i in range(1, len(pvals) + 1)] if not np.isnan(np.array(pvals)).all(): gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=covariance) sample = gmm.predict(indexes, [pvals])[0][0] else: sample = np.nan else: # gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=covariance) sample = 0 for ind, wi in enumerate(w): sample += wi * mean[ind][0] else: sample = np.nan return sample
def test_regression_with_custom_mean_covar_as_lists(): gmm = GMM(n_components=2, priors=[0.5, 0.5], means=[[0, 1], [1, 2]], covariances=[[[1, 0], [0, 1]], [[1, 0], [0, 1]]]) y = gmm.predict([0], [[0]]) assert_array_almost_equal(y, [[1.37754067]])
def choose(self, pvalues, method, outcome): ''' Randomly choose state of node from probability distribution conditioned on *pvalues*. This method has two parts: (1) determining the proper probability distribution, and (2) using that probability distribution to determine an outcome. Arguments: 1. *pvalues* -- An array containing the assigned states of the node's parents. This must be in the same order as the parents appear in ``self.Vdataentry['parents']``. The function creates a Gaussian distribution in the manner described in :doc:`lgbayesiannetwork`, and samples from that distribution, returning its outcome. ''' random.seed() sample = 0 if method == 'simple': # calculate Bayesian parameters (mean and variance) mean = self.Vdataentry["mean_base"] if (self.Vdataentry["parents"] != None): for x in range(len(self.Vdataentry["parents"])): if (pvalues[x] != "default"): mean += pvalues[x] * self.Vdataentry["mean_scal"][x] else: print( "Attempted to sample node with unassigned parents." ) variance = self.Vdataentry["variance"] sample = random.gauss(mean, math.sqrt(variance)) else: mean = self.Vdataentry["mean_base"] variance = self.Vdataentry["variance"] w = self.Vdataentry["mean_scal"] n_comp = len(self.Vdataentry["mean_scal"]) if n_comp != 0: if (self.Vdataentry["parents"] != None): indexes = [ i for i in range(1, (len(self.Vdataentry["parents"]) + 1), 1) ] if not np.isnan(np.array(pvalues)).all(): gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=variance) sample = gmm.predict(indexes, [pvalues])[0][0] else: sample = np.nan else: gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=variance) sample = gmm.sample(1)[0][0] else: sample = np.nan return sample
def choose_gmm(self, pvalues, outcome): ''' Randomly choose state of node from probability distribution conditioned on *pvalues*. This method has two parts: (1) determining the proper probability distribution, and (2) using that probability distribution to determine an outcome. Arguments: 1. *pvalues* -- An array containing the assigned states of the node's parents. This must be in the same order as the parents appear in ``self.Vdataentry['parents']``. The function creates a Gaussian distribution in the manner described in :doc:`lgbayesiannetwork`, and samples from that distribution, returning its outcome. ''' random.seed() # calculate Bayesian parameters (mean and variance) s = 0 mean = self.Vdataentry["mean_base"] variance = self.Vdataentry["variance"] w = self.Vdataentry["mean_scal"] n_comp = len(self.Vdataentry["mean_scal"]) indexes = [ i for i in range(1, (len(self.Vdataentry["parents"]) + 1), 1) ] if (self.Vdataentry["parents"] != None): # for x in range(len(self.Vdataentry["parents"])): # if (pvalues[x] != "default"): # X.append(pvalues[x]) # else: # print ("Attempted to sample node with unassigned parents.") if not np.isnan(np.array(pvalues)).any(): gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=variance) s = gmm.predict(indexes, [pvalues])[0][0] else: s = np.nan else: gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=variance) s = gmm.sample(1)[0][0] # draw random outcome from Gaussian # note that this built in function takes the standard deviation, not the # variance, thus requiring a square root return s
def test_regression_with_2d_input(): """Test regression with GMM and two-dimensional input.""" random_state = check_random_state(0) n_samples = 200 x = np.linspace(0, 2, n_samples)[:, np.newaxis] y1 = 3 * x[:n_samples / 2] + 1 y2 = -3 * x[n_samples / 2:] + 7 noise = random_state.randn(n_samples, 1) * 0.01 y = np.vstack((y1, y2)) + noise samples = np.hstack((x, x[::-1], y)) gmm = GMM(n_components=2, random_state=random_state) gmm.from_samples(samples) pred = gmm.predict(np.array([0, 1]), np.hstack((x, x[::-1]))) mse = np.sum((y - pred) ** 2) / n_samples
def test_regression_with_2d_input(): """Test regression with GMM and two-dimensional input.""" random_state = check_random_state(0) n_samples = 200 x = np.linspace(0, 2, n_samples)[:, np.newaxis] y1 = 3 * x[:n_samples // 2] + 1 y2 = -3 * x[n_samples // 2:] + 7 noise = random_state.randn(n_samples, 1) * 0.01 y = np.vstack((y1, y2)) + noise samples = np.hstack((x, x[::-1], y)) gmm = GMM(n_components=2, random_state=random_state) gmm.from_samples(samples) pred = gmm.predict(np.array([0, 1]), np.hstack((x, x[::-1]))) mse = np.sum((y - pred)**2) / n_samples
def test_regression_without_noise(): """Test regression without noise.""" random_state = check_random_state(0) n_samples = 200 x = np.linspace(0, 2, n_samples)[:, np.newaxis] y1 = 3 * x[:n_samples / 2] + 1 y2 = -3 * x[n_samples / 2:] + 7 y = np.vstack((y1, y2)) samples = np.hstack((x, y)) gmm = GMM(n_components=2, random_state=random_state) gmm.from_samples(samples) assert_array_almost_equal(gmm.priors, 0.5 * np.ones(2), decimal=2) assert_array_almost_equal(gmm.means[0], np.array([1.5, 2.5]), decimal=2) assert_array_almost_equal(gmm.means[1], np.array([0.5, 2.5]), decimal=1) pred = gmm.predict(np.array([0]), x) mse = np.sum((y - pred) ** 2) / n_samples assert_less(mse, 0.01)
def test_regression_without_noise(): """Test regression without noise.""" random_state = check_random_state(0) n_samples = 200 x = np.linspace(0, 2, n_samples)[:, np.newaxis] y1 = 3 * x[:n_samples // 2] + 1 y2 = -3 * x[n_samples // 2:] + 7 y = np.vstack((y1, y2)) samples = np.hstack((x, y)) gmm = GMM(n_components=2, random_state=random_state) gmm.from_samples(samples) assert_array_almost_equal(gmm.priors, 0.5 * np.ones(2), decimal=2) assert_array_almost_equal(gmm.means[0], np.array([1.5, 2.5]), decimal=2) assert_array_almost_equal(gmm.means[1], np.array([0.5, 2.5]), decimal=1) pred = gmm.predict(np.array([0]), x) mse = np.sum((y - pred)**2) / n_samples assert_less(mse, 0.01)
def predict(node_info: Dict[str, Dict[str, CondMixtureGaussParams]], pvals: List[Union[str, float]]) -> Optional[float]: """ Function to get prediction from ConditionalMixtureGaussian node params: node_info: nodes info from distributions pvals: parent values """ dispvals = [] lgpvals = [] for pval in pvals: if ((isinstance(pval, str)) | ((isinstance(pval, int)))): dispvals.append(pval) else: lgpvals.append(pval) lgdistribution = node_info["hybcprob"][str(dispvals)] mean = lgdistribution["mean"] covariance = lgdistribution["covars"] w = lgdistribution["coef"] if len(w) != 0: if len(lgpvals) != 0: indexes = [i for i in range(1, (len(lgpvals) + 1), 1)] if not np.isnan(np.array(lgpvals)).all(): n_comp = len(w) gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=covariance) sample = gmm.predict(indexes, [lgpvals])[0][0] else: sample = np.nan else: # n_comp = len(w) # gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=covariance) sample = 0 for ind, wi in enumerate(w): sample += wi * mean[ind][0] else: sample = np.nan return sample
X_test = np.linspace(0, 2 * np.pi, 100) mean, covariance = mvn.predict(np.array([0]), X_test[:, np.newaxis]) plt.figure(figsize=(10, 5)) plt.subplot(1, 2, 1) plt.title("Linear: $p(Y | X) = \mathcal{N}(\mu_{Y|X}, \Sigma_{Y|X})$") plt.scatter(X[:, 0], X[:, 1]) y = mean.ravel() s = covariance.ravel() plt.fill_between(X_test, y - s, y + s, alpha=0.2) plt.plot(X_test, y, lw=2) n_samples = 100 X = np.ndarray((n_samples, 2)) X[:, 0] = np.linspace(0, 2 * np.pi, n_samples) X[:, 1] = np.sin(X[:, 0]) + random_state.randn(n_samples) * 0.1 gmm = GMM(n_components=3, random_state=0) gmm.from_samples(X) Y = gmm.predict(np.array([0]), X_test[:, np.newaxis]) plt.subplot(1, 2, 2) plt.title("Mixture of Experts: $p(Y | X) = \Sigma_k \pi_{k, Y|X} " "\mathcal{N}_{k, Y|X}$") plt.scatter(X[:, 0], X[:, 1]) plot_error_ellipses(plt.gca(), gmm, colors=["r", "g", "b"]) plt.plot(X_test, Y.ravel(), c="k", lw=2) plt.show()
# Load the model: with open(gmm_file, 'rb') as f: gmm = pickle.load(f) ###################### # Evaluate the model # ###################### N_test = 20 i_test = np.random.choice(range(len(data)), N_test, replace=False) X_data = df.drop(actions, axis=1).to_numpy()[i_test, :] Y_data = df[actions].to_numpy()[i_test, :] X_indices = np.array( list(range(dim_s)) + list(range(dim_s + dim_a, dim_t))) Y_pred = gmm.predict(X_indices, X_data) abs_errors = abs(Y_pred - Y_data).mean(axis=0) print('Absolute errors: %g %g' % tuple(abs_errors)) print(Y_data) print(Y_pred) exit(0) # Load the model: with open(gmm_file, 'rb') as f: gmm = pickle.load(f) ####################### # Load the trial data # #######################
random_state = check_random_state(0) x_axes = np.array([0]) #x-axis y_axes = np.array([1]) #y-axis n_samples = 100 X = np.ndarray((n_samples, 2)) X[:, 1] = np.linspace(0, 2 * np.pi, n_samples) X[:, 0] = np.sin(X[:, 1]) + random_state.randn(n_samples) * 0.1 gmm = GMM(n_components=3, random_state=0) gmm.from_samples(X) X_test = np.linspace(-1.5, 1.5) X_test = X_test[:, np.newaxis] Y = gmm.predict(x_axes, X_test) gmm2 = mixture.GMM(n_components=3, covariance_type='full') gmm2.fit(X) color_iter = itertools.cycle(['r', 'g', 'b', 'c', 'm']) for i, (clf, title) in enumerate([(gmm2, 'GMM')]): splot = plt.subplot(2, 1, i + 1) Y_ = clf.predict(X) for i, (mean, covar, color) in enumerate(zip( clf.means_, clf._get_covars(), color_iter)): v, w = linalg.eigh(covar) u = w[0] / linalg.norm(w[0]) if not np.any(Y_ == i):
random_state = check_random_state(0) X_test = np.linspace(0, 2 * np.pi, 100) Y_test = np.linspace(-1.5, 1.5) plt.figure(figsize=(10, 5)) n_samples = 100 X = np.ndarray((n_samples, 2)) X[:, 0] = np.linspace(0, 2 * np.pi, n_samples) X[:, 1] = np.sin(X[:, 0]) + random_state.randn(n_samples) * 0.1 gmm = GMM(n_components=3, random_state=0) gmm.from_samples(X) Y_x = gmm.predict(np.array([0]), X_test[:, np.newaxis]) Y_y = gmm.predict(np.array([1]), Y_test[:, np.newaxis]) plt.subplot(1, 2, 1) plt.title("Mixture of Experts: $p(Y | X) = \Sigma_k \pi_{k, Y|X} " "\mathcal{N}_{k, Y|X}$") plt.scatter(X[:, 0], X[:, 1]) plot_error_ellipses(plt.gca(), gmm, colors=["r", "g", "b"]) plt.plot(X_test, Y_x.ravel(), c="k", lw=2) plt.plot(Y_y.ravel(), Y_test, c="k", lw=2) X2 = np.loadtxt("samples", unpack=True) X2_test = np.linspace(-7.0, 4.0)#X2[:, 0] Y2_test = np.linspace(-4.0, 6.0) gmm2 = GMM(n_components=4,random_state=0)
def choose_gmm(self, pvalues, outcome): ''' Randomly choose state of node from probability distribution conditioned on *pvalues*. This method has two parts: (1) determining the proper probability distribution, and (2) using that probability distribution to determine an outcome. Arguments: 1. *pvalues* -- An array containing the assigned states of the node's parents. This must be in the same order as the parents appear in ``self.Vdataentry['parents']``. The function creates a Gaussian distribution in the manner described in :doc:`lgbayesiannetwork`, and samples from that distribution, returning its outcome. ''' random.seed() # split parents by type dispvals = [] lgpvals = [] for pval in pvalues: if (isinstance(pval, str)): dispvals.append(pval) else: lgpvals.append(pval) # error check try: a = dispvals[0] a = lgpvals[0] except IndexError: #print ("Did not find LG and discrete type parents.") s = "Did not find LG and discrete type parents." # find correct Gaussian lgdistribution = self.Vdataentry["hybcprob"][str(dispvals)] s = 0 # calculate Bayesian parameters (mean and variance) mean = lgdistribution["mean_base"] variance = lgdistribution["variance"] w = lgdistribution["mean_scal"] #if (self.Vdataentry["parents"] != None): if (len(lgpvals) != 0): if isinstance(mean, list): indexes = [i for i in range (1, (len(lgpvals)+1), 1)] # for x in range(len(lgpvals)): # if (lgpvals[x] != "default"): # X.append(lgpvals[x]) # else: # # temporary error check # print ("Attempted to sample node with unassigned parents.") if not np.isnan(np.array(lgpvals)).any(): n_comp = len(w) gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=variance) s = gmm.predict(indexes, [lgpvals])[0][0] else: s = np.nan else: for x in range(len(lgpvals)): if (lgpvals[x] != "default"): mean += lgpvals[x] * w[x] else: # temporary error check print ("Attempted to sample node with unassigned parents.") s = random.gauss(mean, math.sqrt(variance)) else: if isinstance(mean, list): n_comp = len(w) gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=variance) s = gmm.sample(1) s = s[0][0] else: s = random.gauss(mean, math.sqrt(variance)) # draw random outcome from Gaussian # note that this built in function takes the standard deviation, not the # variance, thus requiring a square root return s
X_data = data[:, :2] y_data = data[:, 2] ####### # GMR # ####### gmm = GMM(n_components=4) gmm.from_samples(data) #x0 = 0 x0 = 1.5 #y0 = 1.5 y0 = -1.5 z0 = np.squeeze( gmm.predict(np.array([0, 1]), np.array([x0, y0])[np.newaxis, :])) dxdy = np.squeeze( gmm.condition_derivative(np.array([0, 1]), np.array([x0, y0]))) print('z( %g, %g ):' % (x0, y0), z0) print('dydx( %g, %g ):' % (x0, y0), dxdy) Zp = np.zeros_like(Zr) for i, x in enumerate(x_scale): for j, y in enumerate(y_scale): Zp[j][i] = np.squeeze( gmm.predict(np.array([0, 1]), np.array([x, y])[np.newaxis, :])) ######### # PLOTS # #########
def choose(self, pvalues, method, outcome): ''' Randomly choose state of node from probability distribution conditioned on *pvalues*. This method has two parts: (1) determining the proper probability distribution, and (2) using that probability distribution to determine an outcome. Arguments: 1. *pvalues* -- An array containing the assigned states of the node's parents. This must be in the same order as the parents appear in ``self.Vdataentry['parents']``. The function goes to the entry of ``"cprob"`` that matches the outcomes of its discrete parents. Then, it constructs a Gaussian distribution based on its Gaussian parents and the parameters found at that entry. Last, it samples from that distribution and returns its outcome. ''' random.seed() sample = 0 if method == 'simple': dispvals = [] lgpvals = [] for pval in pvalues: if ((isinstance(pval, str)) | ((isinstance(pval, int)))): dispvals.append(pval) else: lgpvals.append(pval) lgdistribution = self.Vdataentry["hybcprob"][str(dispvals)] mean = lgdistribution["mean_base"] if (self.Vdataentry["parents"] != None): for x in range(len(lgpvals)): if (lgpvals[x] != "default"): mean += lgpvals[x] * lgdistribution["mean_scal"][x] else: print ("Attempted to sample node with unassigned parents.") variance = lgdistribution["variance"] sample = random.gauss(mean, math.sqrt(variance)) else: dispvals = [] lgpvals = [] for pval in pvalues: if ((isinstance(pval, str)) | ((isinstance(pval, int)))): dispvals.append(pval) else: lgpvals.append(pval) lgdistribution = self.Vdataentry["hybcprob"][str(dispvals)] mean = lgdistribution["mean_base"] variance = lgdistribution["variance"] w = lgdistribution["mean_scal"] if len(w) != 0: if (len(lgpvals) != 0): indexes = [i for i in range (1, (len(lgpvals)+1), 1)] if not np.isnan(np.array(lgpvals)).all(): n_comp = len(w) gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=variance) sample = gmm.predict(indexes, [lgpvals])[0][0] else: sample = np.nan else: n_comp = len(w) gmm = GMM(n_components=n_comp, priors=w, means=mean, covariances=variance) sample = gmm.sample(1)[0][0] else: sample = np.nan return sample
plt.subplot(1, 2, 1) plt.title("Linear: $p(Y | X) = \mathcal{N}(\mu_{Y|X}, \Sigma_{Y|X})$") plt.scatter(X[:, 0], X[:, 1]) y = mean.ravel() s = covariance.ravel() plt.fill_between(X_test, y - s, y + s, alpha=0.2) plt.plot(X_test, y, lw=2) n_samples = 100 X = np.ndarray((n_samples, 2)) X[:, 0] = np.linspace(0, 2 * np.pi, n_samples) X[:, 1] = np.sin(X[:, 0]) + random_state.randn(n_samples) * 0.1 gmm = GMM(n_components=3, random_state=0) gmm.from_samples(X) Y = gmm.predict(np.array([0]), X_test[:, np.newaxis]) #x = 1.5 x = 1.65 #x = 3 y = np.squeeze( gmm.predict(np.array([0]), np.array([ x ])[np.newaxis,:] ) ) dxdy = np.squeeze( gmm.condition_derivative( np.array([0]), np.array([ x ]) ) ) print( 'y( %g ):' % x, y ) print( 'dydx( %g ):' % x, dxdy ) plt.subplot(1, 2, 2) plt.title("Mixture of Experts: $p(Y | X) = \Sigma_k \pi_{k, Y|X} " "\mathcal{N}_{k, Y|X}$") plt.scatter(X[:, 0], X[:, 1]) plot_error_ellipses(plt.gca(), gmm, colors=["r", "g", "b"]) plt.plot(X_test, Y.ravel(), c="k", lw=2) d = 0.5