Source code for ex_fuzzy.centroid

# -*- coding: utf-8 -*-
"""
This is the source file that contains functions to compute centroids for the case of IV fuzzy sets,
which are commonly used when using the IV-T2 fuzzy sets.
"""
import numpy as np


[docs] def center_of_masses(z: np.array, w: np.array) -> np.array: ''' Computes the ponderated centroid with normalized weighting. :param z: Vector of the referencial values. :param w: Vector of the fuzzy memberships. :return: The ponderated sum. ''' return z @ w / np.sum(w)
[docs] def compute_centroid_t2_l(z: np.array, memberships: np.array) -> float: ''' Computes the Karnik and Mendel algorithm to find the centroid of an IV fuzzy set. :param z: Vector of the referencial values. :param memberships: vector of the fuzzy memberships. :return: The centroid. ''' centros = np.mean(memberships, axis=1) w = centros yhat = center_of_masses(z, w) yhat_2 = None while(yhat != yhat_2): try: k = np.argwhere((z - yhat) >= 0)[-1][0] k = min(len(centros)-1, k) except IndexError: k = 0 # k_vector = np.argwhere((z - yhat) > 0) # k = k_vector[0][0] + 1 w[0:k] = memberships[:, 1][:k] w[k:] = memberships[:, 0][k:] yhat_2 = yhat yhat = center_of_masses(z, w) return yhat
[docs] def compute_centroid_t2_r(z: np.array, memberships: np.array) -> float: ''' Computes the Karnik and Mendel algorithm to find the right component of a centroid of an IV fuzzy set. :param z: Vector of the referencial values. :param memberships: vector of the fuzzy memberships. :return: The lowest membership of the centroid. ''' centros = np.mean(memberships, axis=1) w = centros yhat = center_of_masses(z, w) yhat_2 = None while(yhat != yhat_2): try: k = np.argwhere((z - yhat) >= 0)[-1][0] k = min(len(centros)-1, k) except IndexError: k = 0 w[0:k+1] = memberships[:, 0][:k+1] w[k+1:] = memberships[:, 1][k+1:] yhat_2 = yhat yhat = center_of_masses(z, w) return yhat
[docs] def consequent_centroid_r(antecedent_memberships: np.array, centroids_r: np.array) -> float: ''' Computes the Karnik and Mendel algorithm to find the right component of a centroid of an IV fuzzy set using the centroids of the consequents and the antecedents memeberships. :param antecedent_memberships: M x 2 matrix. M rules and iv dimension (2). Vector of memberships. :param centroids_r: M sized vector. Contains the referencial values. :return: the IV centroid. ''' memberships_left = antecedent_memberships[:, 0] memberships_right = antecedent_memberships[:, 1] initial_f = (memberships_left + memberships_right) / 2 yhat = center_of_masses(centroids_r, initial_f) yhat2 = None while(yhat != yhat2): try: r_R = np.argwhere((yhat - centroids_r) >= 0)[-1][0] r_R = min(len(centroids_r)-1, r_R) except IndexError: r_R = 0 new_memberships = initial_f new_memberships[0:r_R+1] = memberships_left[0:r_R+1] new_memberships[r_R+1:] = memberships_right[r_R+1:] yhat2 = yhat if np.sum(new_memberships) == 0: yhat = 0 else: yhat = center_of_masses(centroids_r, new_memberships) return yhat2
[docs] def consequent_centroid_l(antecedent_memberships: np.array, centroids_l: np.array) -> float: ''' Computes the Karnik and Mendel algorithm to find the left component of a centroid of an IV fuzzy set using the centroids of the consequents and the antecedent memberships. :param antecedent_memberships: M x 2 matrix. M rules and iv dimension (2). Vector of memberships. :param centroids_r: M sized vector. Contains the referencial values. :return: the IV centroid. ''' memberships_left = antecedent_memberships[:, 0] memberships_right = antecedent_memberships[:, 1] initial_f = (memberships_left + memberships_right) / 2 # (memberships_right * centroids_r) / np.sum(memberships_right) yhat = center_of_masses(centroids_l, initial_f) yhat2 = -100 #R = np.where(yhat - centroids_r)[0] while(yhat != yhat2): try: r_R = np.argwhere((yhat - centroids_l) >= 0)[-1][0] r_R = min(len(centroids_l)-1, r_R) except IndexError: r_R = 0 new_memberships = initial_f new_memberships[0:r_R+1] = memberships_right[0:r_R+1] new_memberships[r_R+1:] = memberships_left[r_R+1:] yhat2 = yhat if np.sum(new_memberships) == 0: yhat = 0 else: yhat = center_of_masses(centroids_l, new_memberships) return yhat2
[docs] def compute_centroid_iv(z: np.array, memberships: np.array) -> np.array: ''' Computes Karnik and Mendel algorithm to find the centroid of a iv fuzzy set. :param z: Vector of the referencial values. :param memberships: vector of the fuzzy memberships. :return: The centroid. ''' res = np.zeros((2,)) res[0] = compute_centroid_t2_l(z, memberships) res[1] = compute_centroid_t2_r(z, memberships) return res
[docs] def consequent_centroid(antecedent_memberships: np.array, centroids: np.array) -> np.array: ''' Computes Karnik and Mendel algorithm to find the centroid of a consequent iv fuzzy set given the centroids of the consequents and the antecedents memberships. :param antecedent_memberships: M x 2 matrix. M rules and iv dimension (2). Vector of memberships. :param centroids: M x 2 matrix. M rules and iv dimension (2). Vector of centroids. :return: The centroid. ''' centroids_l = centroids[:, 0] centroids_r = centroids[:, 1] res = np.zeros((2,)) res[0] = consequent_centroid_l(antecedent_memberships, centroids_l) res[1] = consequent_centroid_r(antecedent_memberships, centroids_r) return res