class WorkingMemory:
    def __init__(self, max_capacity=8):
        # Initialize the working memory with a capacity of 8 slots for simplicity.
        self.slots = [[] for _ in range(max_capacity)]
        self.active_slot_index = None  # Track which slot is currently active.
        self.attention = 0.5  # Initial attention level to determine which slot has focus.

    def add_to_memory(self, item):
        """
        Adds an item to the working memory based on available slots and capacity.
        :param item: The new information or data to be added.
        """
        if not self.is_full():
            slot_index = self.determine_best_slot(item)
            self.slots[slot_index].append(item)
            if self.active_slot_index is None:
                self.active_slot_index = slot_index
        else:
            print("Working memory is full. Cannot add more items.")

    def determine_best_slot(self, item):
        """
        Determines the best slot to store new information.
        :param item: The new piece of information or data.
        :return: Index of the slot where the item will be added.
        """
        # Here you can use a heuristic based on relevance, recency, or any other metric.
        scores = [self.get_relevance_score(slot[-1], item) for slot in self.slots if len(slot) > 0]
        max_index, _ = max(enumerate(scores), key=lambda x: x[1])
        return max_index

    def get_relevance_score(self, current_item, new_item):
        """
        A simple relevance scoring function.
        :param current_item: The item currently stored in the slot.
        :param new_item: The new item to be added.
        :return: Relevance score between 0 and 1.
        """
        # Example: Count common words or use cosine similarity for text-based items.
        return len(set(current_item.split()).intersection(new_item.split())) / max(len(current_item), len(new_item))

    def update_active_slot(self, new_info):
        """
        Updates the currently active slot with new information.
        :param new_info: New data to update the current active slot.
        """
        if self.active_slot_index is not None:
            # Replace or append new info based on existing content.
            self.slots[self.active_slot_index][-1] = new_info
        else:
            print("No active slot exists. Cannot update.")

    def is_full(self):
        """
        Checks if the working memory is full.
        :return: True if the working memory capacity is reached, False otherwise.
        """
        return all(len(slot) > 0 for slot in self.slots)

    def recall_information(self, keyword):
        """
        Recalls information from the working memory based on a keyword or content.
        :param keyword: A string representing the keyword to search for.
        :return: List of items matching the keyword.
        """
        return [slot[-1] for slot in self.slots if keyword.lower() in ' '.join(slot).lower()]

    def focus_attention(self, new_slot_index):
        """
        Changes the active slot based on attention allocation.
        :param new_slot_index: The index of the new active slot.
        """
        self.active_slot_index = new_slot_index