

"""simple docstring"""





import warnings

import numpy as np
import pandas as pd
from matplotlib import pyplot as plt
from sklearn.metrics import pairwise_distances

warnings.filterwarnings('ignore')

_a					 =				'K-MEANS-CLUST/ '




def     _A    (    UpperCamelCase_	:			Optional[int],     UpperCamelCase_	:			str,     UpperCamelCase_	:			Optional[Any]=None)      ->		List[str]:
   '''simple docstring'''


   if seed is not None:  # useful for obtaining consistent results
      np.random.seed(UpperCamelCase_)
   __lowercase								=		data.shape[0]  # number of data points

   # Pick K indices from range [0, N).
   __lowercase								=		np.random.randint(0,     UpperCamelCase_,     UpperCamelCase_)

   # Keep centroids as dense format, as many entries will be nonzero due to averaging.
   # As long as at least one document in a cluster contains a word,
   # it will carry a nonzero weight in the TF-IDF vector of the centroid.
   __lowercase								=		data[rand_indices, :]

   return centroids




def     _A    (    UpperCamelCase_	:			Union[str, Any],     UpperCamelCase_	:			int)      ->		Dict:
   '''simple docstring'''


   return pairwise_distances(UpperCamelCase_,     UpperCamelCase_,     metric="euclidean")




def     _A    (    UpperCamelCase_	:			List[str],     UpperCamelCase_	:			Dict)      ->		int:
   '''simple docstring'''


   __lowercase								=		centroid_pairwise_dist(UpperCamelCase_,     UpperCamelCase_)

   # Compute cluster assignments for each data point:
   # Fill in the blank (RHS only)
   __lowercase								=		np.argmin(UpperCamelCase_,     axis=1)

   return cluster_assignment




def     _A    (    UpperCamelCase_	:			Dict,     UpperCamelCase_	:			str,     UpperCamelCase_	:			Dict)      ->		Optional[Any]:
   '''simple docstring'''


   __lowercase								=		[]
   for i in range(UpperCamelCase_):
      # Select all data points that belong to cluster i. Fill in the blank (RHS only)
      __lowercase								=		data[cluster_assignment == i]
      # Compute the mean of the data points. Fill in the blank (RHS only)
      __lowercase								=		member_data_points.mean(axis=0)
      new_centroids.append(UpperCamelCase_)
   __lowercase								=		np.array(UpperCamelCase_)

   return new_centroids




def     _A    (    UpperCamelCase_	:			Tuple,     UpperCamelCase_	:			Tuple,     UpperCamelCase_	:			Optional[int],     UpperCamelCase_	:			List[Any])      ->		str:
   '''simple docstring'''


   __lowercase								=		0.0
   for i in range(UpperCamelCase_):
      # Select all data points that belong to cluster i. Fill in the blank (RHS only)
      __lowercase								=		data[cluster_assignment == i, :]

      if member_data_points.shape[0] > 0:  # check if i-th cluster is non-empty
         # Compute distances from centroid to data points (RHS only)
         __lowercase								=		pairwise_distances(
             UpperCamelCase_,     [centroids[i]],     metric="euclidean")
         __lowercase								=		distances**2
         heterogeneity += np.sum(UpperCamelCase_)

   return heterogeneity




def     _A    (    UpperCamelCase_	:			Optional[Any],     UpperCamelCase_	:			Dict)      ->		List[str]:
   '''simple docstring'''


   plt.figure(figsize=(7, 4))
   plt.plot(UpperCamelCase_,     linewidth=4)
   plt.xlabel("# Iterations")
   plt.ylabel("Heterogeneity")
   plt.title(F"""Heterogeneity of clustering over time, K={k:d}""")
   plt.rcParams.update({"font.size": 16})
   plt.show()




def     _A    (    UpperCamelCase_	:			Tuple,     UpperCamelCase_	:			Optional[Any],     UpperCamelCase_	:			Union[str, Any],     UpperCamelCase_	:			List[Any]=500,     UpperCamelCase_	:			Any=None,     UpperCamelCase_	:			Optional[int]=False)      ->		Union[str, Any]:
   '''simple docstring'''


   __lowercase								=		initial_centroids[:]
   __lowercase								=		None

   for itr in range(UpperCamelCase_):
      if verbose:
         print(UpperCamelCase_,     end="")

      # 1. Make cluster assignments using nearest centroids
      __lowercase								=		assign_clusters(UpperCamelCase_,     UpperCamelCase_)

      # 2. Compute a new centroid for each of the k clusters, averaging all data
      #    points assigned to that cluster.
      __lowercase								=		revise_centroids(UpperCamelCase_,     UpperCamelCase_,     UpperCamelCase_)

      # Check for convergence: if none of the assignments changed, stop
      if (
          prev_cluster_assignment is not None
          and (prev_cluster_assignment == cluster_assignment).all()
      ):
         break

      # Print number of new assignments
      if prev_cluster_assignment is not None:
         __lowercase								=		np.sum(prev_cluster_assignment != cluster_assignment)
         if verbose:
            print(
                F"""    {num_changed:5d} elements changed their cluster assignment.""")

        # Record heterogeneity convergence metric
      if record_heterogeneity is not None:
         # YOUR CODE HERE
         __lowercase								=		compute_heterogeneity(UpperCamelCase_,     UpperCamelCase_,     UpperCamelCase_,     UpperCamelCase_)
         record_heterogeneity.append(UpperCamelCase_)

      __lowercase								=		cluster_assignment[:]

   return centroids, cluster_assignment


# Mock test below
if False:  # change to true to run this test case.
   from sklearn import datasets as ds

   _a					 =				ds.load_iris()
   _a					 =				3
   _a					 =				[]
   _a					 =				get_initial_centroids(dataset['data'], k, seed=0)
   _a ,		_a					 =				kmeans(
       dataset['data'],
       k,
       initial_centroids,
       maxiter=4_00,
       record_heterogeneity=heterogeneity,
       verbose=True,
   )
   plot_heterogeneity(heterogeneity, k)




def     _A    (    UpperCamelCase_	:			pd.DataFrame,     UpperCamelCase_	:			np.ndarray,     UpperCamelCase_	:			Union[str, Any]=None)      ->		pd.DataFrame:
   '''simple docstring'''


   if fill_missing_report:
      __lowercase								=		df.fillna(value=UpperCamelCase_)
   __lowercase								=		1
   __lowercase								=		df.select_dtypes(np.number).columns
   __lowercase								=		(
       df.groupby(["Cluster"])[  # construct report dataframe
           numeric_cols
       ]  # group by cluster number
       .agg(
           [
               ("sum", np.sum),
               ("mean_with_zeros", lambda UpperCamelCase_: np.mean(np.nan_to_num(UpperCamelCase_))),
               ("mean_without_zeros", lambda UpperCamelCase_: x.replace(0,     np.NaN).mean()),
               (
                   "mean_25-75",
                   lambda UpperCamelCase_: np.mean(
                       np.nan_to_num(
                           sorted(UpperCamelCase_)[
                               round(len(UpperCamelCase_) * 25 / 100) : round(len(UpperCamelCase_) * 75 / 100)
                           ])),
               ),
               ("mean_with_na", np.mean),
               ("min", lambda UpperCamelCase_: x.min()),
               ("5%", lambda UpperCamelCase_: x.quantile(0.05)),
               ("25%", lambda UpperCamelCase_: x.quantile(0.25)),
               ("50%", lambda UpperCamelCase_: x.quantile(0.50)),
               ("75%", lambda UpperCamelCase_: x.quantile(0.75)),
               ("95%", lambda UpperCamelCase_: x.quantile(0.95)),
               ("max", lambda UpperCamelCase_: x.max()),
               ("count", lambda UpperCamelCase_: x.count()),
               ("stdev", lambda UpperCamelCase_: x.std()),
               ("mode", lambda UpperCamelCase_: x.mode()[0]),
               ("median", lambda UpperCamelCase_: x.median()),
               ("# > 0", lambda UpperCamelCase_: (x > 0).sum()),
           ])
       .T.reset_index()
       .rename(index=UpperCamelCase_,     columns={"level_0": "Features", "level_1": "Type"})
   )  # rename columns
   # calculate the size of cluster(count of clientID's)
   __lowercase								=		report[
       (report["Features"] == "dummy") & (report["Type"] == "count")
   ].copy()  # avoid SettingWithCopyWarning
   __lowercase								=		(
       "ClusterSize"  # rename created cluster df to match report column names
   )
   __lowercase								=		"# of Customers"
   __lowercase								=		pd.DataFrame(
       clustersize.iloc[:, 2:].values
       / clustersize.iloc[:, 2:].values.sum())
   __lowercase								=		"% of Customers"  # rename created cluster df to match report column names
   __lowercase								=		"ClusterProportion"
   __lowercase								=		clusterproportion.columns.tolist()
   __lowercase								=		cols[-2:] + cols[:-2]
   __lowercase								=		clusterproportion[cols]  # rearrange columns to match report
   __lowercase								=		report.columns
   __lowercase								=		pd.DataFrame(
       abs(
           report[report["Type"] == "count"].iloc[:, 2:].values
           - clustersize.iloc[:, 2:].values))  # generating df with count of nan values
   __lowercase								=		0
   __lowercase								=		"# of nan"
   __lowercase								=		report[
       report["Type"] == "count"
   ].Features.tolist()  # filling values in order to match report
   __lowercase								=		a.columns.tolist()
   __lowercase								=		cols[-2:] + cols[:-2]
   __lowercase								=		a[cols]  # rearrange columns to match report
   __lowercase								=		report.columns  # rename columns to match report
   __lowercase								=		report.drop(
       report[report.Type == "count"].index)  # drop count values except cluster size
   __lowercase								=		pd.concat(
       [report, a, clustersize, clusterproportion],     axis=0)  # concat report with clustert size and nan values
   __lowercase								=		report["Features"].isin(UpperCamelCase_)
   __lowercase								=		report.columns.tolist()
   __lowercase								=		cols[0:2] + cols[-1:] + cols[2:-1]
   __lowercase								=		report[cols]
   __lowercase								=		{
       "ClusterSize": 9,
       "ClusterProportion": 8,
       "mean_with_zeros": 7,
       "mean_with_na": 6,
       "max": 5,
       "50%": 4,
       "min": 3,
       "25%": 2,
       "75%": 1,
       "# of nan": 0,
       "# > 0": -1,
       "sum_with_na": -2,
   }
   __lowercase								=		(
       report.assign(
           Sortera=lambda UpperCamelCase_: x.Type.map(UpperCamelCase_),     Sortera=lambda UpperCamelCase_: list(reversed(range(len(UpperCamelCase_)))),     )
       .sort_values(["Sorter1", "Mark", "Sorter2"],     ascending=UpperCamelCase_)
       .drop(["Sorter1", "Sorter2"],     axis=1)
   )
   __lowercase								=		""
   __lowercase								=		report.reset_index()
   __lowercase								=		report.drop(columns=["index"])
   return report


if __name__ == "__main__":
   import doctest

   doctest.testmod()







"""simple docstring"""





import unittest

import numpy as np

from transformers.testing_utils import require_torch, require_vision
from transformers.utils import is_torch_available, is_vision_available

from ...test_image_processing_common import ImageProcessingSavingTestMixin, prepare_image_inputs


if is_torch_available():
   import torch

if is_vision_available():
   from PIL import Image

   from transformers import OwlViTImageProcessor




class    _lowerCAmelCase    (      unittest.TestCase  ):







 """simple docstring"""







 def __init__(     self				:     Union[str, Any],   UpperCAmelCase__				:     Dict,   UpperCAmelCase__				:     Optional[int]=7,   UpperCAmelCase__				:     List[str]=3,   UpperCAmelCase__				:     List[Any]=1_8,   UpperCAmelCase__				:     Any=3_0,   UpperCAmelCase__				:     str=4_0_0,   UpperCAmelCase__				:     Union[str, Any]=True,   UpperCAmelCase__				:     Dict=None,   UpperCAmelCase__				:     int=True,   UpperCAmelCase__				:     str=None,   UpperCAmelCase__				:     Dict=True,   UpperCAmelCase__				:     str=[0.48_145_466, 0.4_578_275, 0.40_821_073],   UpperCAmelCase__				:     Dict=[0.26_862_954, 0.26_130_258, 0.27_577_711],   UpperCAmelCase__				:     Any=True,   ):
    __lowercase								=		parent
    __lowercase								=		batch_size
    __lowercase								=		num_channels
    __lowercase								=		image_size
    __lowercase								=		min_resolution
    __lowercase								=		max_resolution
    __lowercase								=		do_resize
    __lowercase								=		size if size is not None else {"height": 1_8, "width": 1_8}
    __lowercase								=		do_center_crop
    __lowercase								=		crop_size if crop_size is not None else {"height": 1_8, "width": 1_8}
    __lowercase								=		do_normalize
    __lowercase								=		image_mean
    __lowercase								=		image_std
    __lowercase								=		do_convert_rgb



 def    _lowercase					(     self				:     List[str]      ):
    return {
        "do_resize": self.do_resize,
        "size": self.size,
        "do_center_crop": self.do_center_crop,
        "crop_size": self.crop_size,
        "do_normalize": self.do_normalize,
        "image_mean": self.image_mean,
        "image_std": self.image_std,
        "do_convert_rgb": self.do_convert_rgb,
    }







@require_torch
@require_vision
class    _lowerCAmelCase    (      lowercase	,unittest.TestCase  ):







 """simple docstring"""







 __UpperCAmelCase      :   List[str]  						=      OwlViTImageProcessor if is_vision_available() else None


 def    _lowercase					(     self				:     Dict      ):
    __lowercase								=		OwlViTImageProcessingTester(self      )


 @property
 def    _lowercase					(     self				:     int      ):
    return self.image_processor_tester.prepare_image_processor_dict()


 def    _lowercase					(     self				:     Tuple      ):
    __lowercase								=		self.image_processing_class(**self.image_processor_dict      )
    self.assertTrue(hasattr(UpperCAmelCase__,   "do_resize"      )      )
    self.assertTrue(hasattr(UpperCAmelCase__,   "size"      )      )
    self.assertTrue(hasattr(UpperCAmelCase__,   "do_center_crop"      )      )
    self.assertTrue(hasattr(UpperCAmelCase__,   "center_crop"      )      )
    self.assertTrue(hasattr(UpperCAmelCase__,   "do_normalize"      )      )
    self.assertTrue(hasattr(UpperCAmelCase__,   "image_mean"      )      )
    self.assertTrue(hasattr(UpperCAmelCase__,   "image_std"      )      )
    self.assertTrue(hasattr(UpperCAmelCase__,   "do_convert_rgb"      )      )


 def    _lowercase					(     self				:     Dict      ):
    __lowercase								=		self.image_processing_class.from_dict(self.image_processor_dict      )
    self.assertEqual(image_processor.size,   {"height": 1_8, "width": 1_8}      )
    self.assertEqual(image_processor.crop_size,   {"height": 1_8, "width": 1_8}      )

    __lowercase								=		self.image_processing_class.from_dict(self.image_processor_dict,   size=4_2,   crop_size=8_4      )
    self.assertEqual(image_processor.size,   {"height": 4_2, "width": 4_2}      )
    self.assertEqual(image_processor.crop_size,   {"height": 8_4, "width": 8_4}      )


 def    _lowercase					(     self				:     Any      ):
    # Initialize image_processing
    __lowercase								=		self.image_processing_class(**self.image_processor_dict      )
    # create random PIL images
    __lowercase								=		prepare_image_inputs(self.image_processor_tester,   equal_resolution=UpperCAmelCase__      )

    for image in image_inputs:
       self.assertIsInstance(UpperCAmelCase__,   Image.Image      )

    # Test not batched input
    __lowercase								=		image_processing(image_inputs[0],   return_tensors="pt"      ).pixel_values
    self.assertEqual(
        encoded_images.shape,   (
            1,
            self.image_processor_tester.num_channels,
            self.image_processor_tester.crop_size["height"],
            self.image_processor_tester.crop_size["width"],
        ),   )

    # Test batched
    __lowercase								=		image_processing(UpperCAmelCase__,   return_tensors="pt"      ).pixel_values
    self.assertEqual(
        encoded_images.shape,   (
            self.image_processor_tester.batch_size,
            self.image_processor_tester.num_channels,
            self.image_processor_tester.crop_size["height"],
            self.image_processor_tester.crop_size["width"],
        ),   )


 def    _lowercase					(     self				:     Optional[Any]      ):
    # Initialize image_processing
    __lowercase								=		self.image_processing_class(**self.image_processor_dict      )
    # create random numpy tensors
    __lowercase								=		prepare_image_inputs(self.image_processor_tester,   equal_resolution=UpperCAmelCase__,   numpify=UpperCAmelCase__      )
    for image in image_inputs:
       self.assertIsInstance(UpperCAmelCase__,   np.ndarray      )

    # Test not batched input
    __lowercase								=		image_processing(image_inputs[0],   return_tensors="pt"      ).pixel_values
    self.assertEqual(
        encoded_images.shape,   (
            1,
            self.image_processor_tester.num_channels,
            self.image_processor_tester.crop_size["height"],
            self.image_processor_tester.crop_size["width"],
        ),   )

    # Test batched
    __lowercase								=		image_processing(UpperCAmelCase__,   return_tensors="pt"      ).pixel_values
    self.assertEqual(
        encoded_images.shape,   (
            self.image_processor_tester.batch_size,
            self.image_processor_tester.num_channels,
            self.image_processor_tester.crop_size["height"],
            self.image_processor_tester.crop_size["width"],
        ),   )



 def    _lowercase					(     self				:     List[str]      ):
    # Initialize image_processing
    __lowercase								=		self.image_processing_class(**self.image_processor_dict      )
    # create random PyTorch tensors
    __lowercase								=		prepare_image_inputs(self.image_processor_tester,   equal_resolution=UpperCAmelCase__,   torchify=UpperCAmelCase__      )
    for image in image_inputs:
       self.assertIsInstance(UpperCAmelCase__,   torch.Tensor      )

    # Test not batched input
    __lowercase								=		image_processing(image_inputs[0],   return_tensors="pt"      ).pixel_values
    self.assertEqual(
        encoded_images.shape,   (
            1,
            self.image_processor_tester.num_channels,
            self.image_processor_tester.crop_size["height"],
            self.image_processor_tester.crop_size["width"],
        ),   )

    # Test batched
    __lowercase								=		image_processing(UpperCAmelCase__,   return_tensors="pt"      ).pixel_values
    self.assertEqual(
        encoded_images.shape,   (
            self.image_processor_tester.batch_size,
            self.image_processor_tester.num_channels,
            self.image_processor_tester.crop_size["height"],
            self.image_processor_tester.crop_size["width"],
        ),   )




