```
class MatchingFilesWindow(tk.Toplevel):
    # Class-level cache to store weak references to dialog instances
    _instances = weakref.WeakValueDictionary()

    def __init__(self, master, input_path, matches=None):
        super().__init__(master)
        self.master = master
        self.input_path = input_path
        self.matches = matches if matches else []
        self.tree = None
        self.create_ui()
        self._populate_initial_data()
        self._start_background_tasks()

    @classmethod
    def show(cls, master, input_path, matches=None):
        """
        Show the MatchingFilesWindow. If an instance with the same master and input_path
        exists, bring it to the front. Otherwise, create a new instance.
        """
        instance = cls.window_exists(master, input_path)

        if instance:
            instance.lift()
            instance.after(1, instance.focus_force)
        else:
            instance = cls(master, input_path, matches)
            key = (id(master), input_path)
            cls._instances[key] = instance

    @classmethod
    def window_exists(cls, master, input_path):
        key = (id(master), input_path)
        instance = cls._instances.get(key)

        if instance and tk.Toplevel.winfo_exists(instance):
            return instance

    def create_ui(self):
        self.title("Duplicate Matches")
        self.resizable(True, True)
        self.master.center_window(self, 800, 400)

        content_frame = ttk.Frame(self, padding=10)
        content_frame.pack(fill=tk.BOTH, expand=True)

        input_label = ttk.Label(content_frame, text=f"Input file: {os.path.basename(self.input_path)}")
        input_label.pack(anchor=tk.W, pady=(0, 5))

        parent_frame = ttk.Frame(content_frame)
        parent_frame.pack(fill=tk.X, pady=(0, 10))

        parent_label = ttk.Label(parent_frame, text="Parent folder:")
        parent_label.pack(side=tk.LEFT)

        parent_path = os.path.dirname(self.input_path)
        parent_path_label = ttk.Label(parent_frame, text=parent_path)
        parent_path_label.pack(side=tk.LEFT, padx=5)

        parent_browse = ttk.Button(parent_frame, text="Browse", command=lambda: open_folder(parent_path))
        parent_browse.pack(side=tk.LEFT)

        tree_frame = ttk.Frame(content_frame)
        tree_frame.pack(fill=tk.BOTH, expand=True)

        columns = ("basename", "size", "murmurhash")
        tree = ttk.Treeview(tree_frame, columns=columns, show='headings')
        self.tree = tree

        tree.heading("basename", text="Basename")
        tree.heading("size", text="File Size")
        tree.heading("murmurhash", text="MurmurHash")

        tree.column("basename", stretch=True, anchor=tk.W)
        tree.column("size", width=100, minwidth=100, stretch=False, anchor=tk.CENTER)
        tree.column("murmurhash", width=150, minwidth=100, stretch=False, anchor=tk.CENTER)

        y_scrollbar = ttk.Scrollbar(tree_frame, orient=tk.VERTICAL, command=tree.yview)
        x_scrollbar = ttk.Scrollbar(tree_frame, orient=tk.HORIZONTAL, command=tree.xview)

        tree.configure(yscroll=y_scrollbar.set, xscroll=x_scrollbar.set)

        tree.grid(row=0, column=0, sticky='nsew')
        y_scrollbar.grid(row=0, column=1, sticky='ns')
        x_scrollbar.grid(row=1, column=0, sticky='ew')

        tree_frame.grid_rowconfigure(0, weight=1)
        tree_frame.grid_columnconfigure(0, weight=1)

        tree.bind("<Double-1>", lambda event: self.on_dbclick_tree(event, tree, os.path.dirname(self.input_path)))

        button_frame = ttk.Frame(self, padding=10)
        button_frame.pack(fill=tk.X, pady=5)

        # Create a container frame to center the buttons
        center_frame = ttk.Frame(button_frame)
        center_frame.pack(expand=True)

        ok_button = ttk.Button(center_frame, text="OK", command=self.destroy)
        self.deduplicate_button = deduplicate_button = ttk.Button(center_frame, text="Deduplicate", command=self.deduplicate)
        deduplicate_button.config(state=tk.DISABLED)

        # Pack buttons horizontally in the center frame
        ok_button.pack(side=tk.LEFT, padx=(0, 5))
        deduplicate_button.pack(side=tk.LEFT, padx=(5, 0))

    def _populate_initial_data(self):
        for dup_basename, _, dup_full_path in self.matches:
            self.tree.insert("", tk.END, values=(dup_basename, "Calculating...", "Calculating..."))

    def _start_background_tasks(self):
        thread = threading.Thread(target=self.compute_hash_and_size, daemon=True)
        thread.start()

    def compute_hash_and_size(self):
        common_hash = None
        for index, (dup_basename, _, dup_full_path) in enumerate(self.matches):
            try:
                with open(dup_full_path, 'rb') as f:
                    content = f.read()

                # Compute the MurmurHash from the file content
                hash_value_int = mmh3.hash(content, seed=0)
                hash_value = hex(hash_value_int & 0xFFFFFFFF)

                # When not same as prev hash, it is assigned None
                common_hash = hash_value_int if common_hash is None or common_hash == hash_value_int else None

                size = os.path.getsize(dup_full_path)
                human_readable_size = self.get_human_readable_size(size)
            except FileNotFoundError:
                human_readable_size, hash_value = "Not Found", "N/A"
            except Exception as e:
                print(f"Error processing {dup_full_path}: {e}")
                human_readable_size, hash_value = "Error", "Error"

            # Schedule the update on the main thread
            self.tree.after(0, self._update_tree_item, index, dup_basename, human_readable_size, hash_value)

        if common_hash:
            self.deduplicate_button.config(state=tk.NORMAL)

    def _update_tree_item(self, index, basename, size, hash_value):
        children = self.tree.get_children()
        if index < len(children):
            self.tree.item(
                children[index],
                values=(basename, size, hash_value)
            )

    def deduplicate(self, event):
        # update this
        # update master
        ...
        # make help dialog single instance

    @staticmethod
    def on_dbclick_tree(event, tree, parent_path):
        region = tree.identify("region", event.x, event.y)
        if region != "cell":
            return
        row_id = tree.identify_row(event.y)

        if not row_id:
            return

        basename = tree.set(row_id, "basename")
        file_path = os.path.join(parent_path, basename)
        if os.path.exists(file_path):
            highlight_files(file_path)
        else:
            messagebox.showerror("File Not Found", f"The file '{file_path}' does not exist.")

    @staticmethod
    def get_human_readable_size(size, decimal_places=2):
        for unit in ['B', 'KB', 'MB', 'GB', 'TB']:
            if size < 1024.0:
                return f"{size:.{decimal_places}f} {unit}"
            size /= 1024.0
        return f"{size:.{decimal_places}f} PB"

```

currently, in order to use the deduplicate feature, a gui is opened, and then a background thread is run and will checksum each file one by one.
now i want to have an option in parent widget to use the deduplicate feature without a gui, meaning that the parent widget can call it to compute checksums and then deduplicate (if the checksums are identical)
i assume this means keeping a weak reference to a tk.TopLevel instance
if the computation are done, then when the parent widget opens the window, it does not recompute again unless `matches` argument differs in content (matches is just a list of files)
there should be a way to recompute+rerender where parent widget can update the `matches` argument while window is opened (or when window is closed, just recompute)
also add a Refresh button, just in case user changes files and we want to allow manual recompute
upon user closing tk.TopLevel, it is destroyed and the weak reference is invalid
please modify the class accordingly