Please select at least one cluster to adjust.
\"))\n", + " return\n", + " adjusting_clusters = True\n", + " # Collect all questions in the selected clusters\n", + " questions_to_adjust = df[df['current_cluster'].isin(selected_clusters)].copy()\n", + " display_selected_clusters()\n", + " display_clusters()\n", + "\n", + "# Function to aggregate clusters\n", + "def aggregate_clusters_func(b):\n", + " \"\"\"\n", + " Aggregates selected clusters by moving their questions up one level.\n", + " \"\"\"\n", + " global df, questions_to_adjust\n", + " if questions_to_adjust.empty:\n", + " with selected_clusters_output:\n", + " display(HTML(\"No clusters selected for aggregation.
\"))\n", + " return\n", + " messages = []\n", + " for idx, row in questions_to_adjust.iterrows():\n", + " current_level = row['current_level']\n", + " try:\n", + " idx_level = levels.index(current_level)\n", + " except ValueError:\n", + " messages.append(f\"Question '{row['question']}' has an invalid current level '{current_level}'.\")\n", + " continue\n", + " if idx_level + 1 >= len(levels):\n", + " messages.append(f\"Question '{row['question']}' is already at the maximum level '{current_level}'.\")\n", + " continue\n", + " new_level = levels[idx_level + 1]\n", + " # Update cluster assignments\n", + " new_cluster = row[f'hierarchical_ward_{new_level}']\n", + " new_cluster_name = row[f'hierarchical_ward_{new_level}_name']\n", + " df.at[idx, 'current_cluster'] = new_cluster\n", + " df.at[idx, 'current_cluster_name'] = new_cluster_name\n", + " df.at[idx, 'current_level'] = new_level\n", + " messages.append(f\"Question '{row['question']}' aggregated to level {new_level}.\")\n", + " # Update the questions_to_adjust DataFrame\n", + " questions_to_adjust = df[df.index.isin(questions_to_adjust.index)].copy()\n", + " display_selected_clusters()\n", + " display_clusters()\n", + " # Display messages\n", + " # with selected_clusters_output:\n", + " # for msg in messages:\n", + " # if \"aggregated\" in msg:\n", + " # display(HTML(f\"{msg}
\"))\n", + " # else:\n", + " # display(HTML(f\"{msg}
\"))\n", + "\n", + "# Function to split clusters\n", + "def split_clusters_func(b):\n", + " \"\"\"\n", + " Splits selected clusters by moving their questions down one level.\n", + " \"\"\"\n", + " global df, questions_to_adjust\n", + " if questions_to_adjust.empty:\n", + " with selected_clusters_output:\n", + " display(HTML(\"No clusters selected for splitting.
\"))\n", + " return\n", + " messages = []\n", + " for idx, row in questions_to_adjust.iterrows():\n", + " current_level = row['current_level']\n", + " try:\n", + " idx_level = levels.index(current_level)\n", + " except ValueError:\n", + " messages.append(f\"Question '{row['question']}' has an invalid current level '{current_level}'.\")\n", + " continue\n", + " if idx_level - 1 < 0:\n", + " messages.append(f\"Question '{row['question']}' is already at the minimum level '{current_level}'.\")\n", + " continue\n", + " new_level = levels[idx_level - 1]\n", + " # Update cluster assignments\n", + " new_cluster = row[f'hierarchical_ward_{new_level}']\n", + " new_cluster_name = row[f'hierarchical_ward_{new_level}_name']\n", + " df.at[idx, 'current_cluster'] = new_cluster\n", + " df.at[idx, 'current_cluster_name'] = new_cluster_name\n", + " df.at[idx, 'current_level'] = new_level\n", + " messages.append(f\"Question '{row['question']}' split to level {new_level}.\")\n", + " # Update the questions_to_adjust DataFrame\n", + " questions_to_adjust = df[df.index.isin(questions_to_adjust.index)].copy()\n", + " display_selected_clusters()\n", + " display_clusters()\n", + " # Display messages\n", + " # with selected_clusters_output:\n", + " # for msg in messages:\n", + " # if \"split\" in msg:\n", + " # display(HTML(f\"{msg}
\"))\n", + " # else:\n", + " # display(HTML(f\"{msg}
\"))\n", + "\n", + "# Function to set clusters to a specific level\n", + "def set_level_clusters_func(b):\n", + " \"\"\"\n", + " Sets selected clusters to a specific level chosen by the user.\n", + " \"\"\"\n", + " global df, questions_to_adjust\n", + " new_level = level_widget.value\n", + " messages = []\n", + " for idx, row in questions_to_adjust.iterrows():\n", + " current_level = row['current_level']\n", + " try:\n", + " # Check if new_level exists in the levels list\n", + " idx_new = levels.index(new_level)\n", + " except ValueError:\n", + " messages.append(f\"Level '{new_level}' is invalid.\")\n", + " continue\n", + " # Update cluster assignments\n", + " new_cluster = row[f'hierarchical_ward_{new_level}']\n", + " new_cluster_name = row[f'hierarchical_ward_{new_level}_name']\n", + " df.at[idx, 'current_cluster'] = new_cluster\n", + " df.at[idx, 'current_cluster_name'] = new_cluster_name\n", + " df.at[idx, 'current_level'] = new_level\n", + " messages.append(f\"Question '{row['question']}' set to level {new_level}.\")\n", + " # Update the questions_to_adjust DataFrame\n", + " questions_to_adjust = df[df.index.isin(questions_to_adjust.index)].copy()\n", + " display_selected_clusters()\n", + " display_clusters()\n", + " # Display messages\n", + " # with selected_clusters_output:\n", + " # for msg in messages:\n", + " # if \"set to\" in msg:\n", + " # display(HTML(f\"{msg}
\"))\n", + " # else:\n", + " # display(HTML(f\"{msg}
\"))\n", + "\n", + "\n", + "# Function to finalize adjustments, save, and flag adjusted questions\n", + "def done_adjusting_func(b):\n", + " \"\"\"\n", + " Finalizes the adjustment process, saves the currently adjusted clusters,\n", + " flags adjusted questions in the original DataFrame, and clears the UI.\n", + " \"\"\"\n", + " global adjusting_clusters, selected_clusters, questions_to_adjust, adjusted_clusters_df\n", + " \n", + " if not questions_to_adjust.empty:\n", + " # Filter questions_to_adjust to only include checked clusters\n", + " checked_ids = {cluster_id for checkbox, cluster_id in adjust_checkboxes if checkbox.value}\n", + " to_adjust_df = questions_to_adjust[questions_to_adjust['current_cluster'].isin(checked_ids)].copy()\n", + " \n", + " # Add 'selected_user_cluster' to questions being adjusted and save them\n", + " #to_adjust_df['selected_user_cluster'] = to_adjust_df['current_cluster_name']\n", + " to_adjust_df.loc[:, 'selected_user_cluster'] = to_adjust_df['current_cluster_name']\n", + "\n", + " adjusted_clusters_df = pd.concat([adjusted_clusters_df, to_adjust_df], ignore_index=True)\n", + " \n", + " # Flag these questions as adjusted in the original DataFrame\n", + " df.loc[to_adjust_df.index, 'flag_adjusted'] = True\n", + "\n", + " # Reset adjustment state variables and clear the UI\n", + " adjusting_clusters = False\n", + " selected_clusters = []\n", + " questions_to_adjust = pd.DataFrame()\n", + " selected_clusters_output.clear_output()\n", + " display_clusters()\n", + " \n", + "# Function to update clusters when initial level changes\n", + "def update_initial_level(change):\n", + " \"\"\"\n", + " Updates the DataFrame and UI when the initial level is changed.\n", + " \"\"\"\n", + " global current_level, df, adjusting_clusters, selected_clusters, questions_to_adjust\n", + " new_initial_level = change['new']\n", + " current_level = new_initial_level\n", + " initialize_df(current_level)\n", + " level_widget.value = current_level # Update the adjustment level to match\n", + " adjusting_clusters = False\n", + " selected_clusters = []\n", + " questions_to_adjust = pd.DataFrame()\n", + " selected_clusters_output.clear_output()\n", + " display_clusters()\n", + "\n", + "def set_clusters_undone(b):\n", + " \"\"\"\n", + " Marks selected adjusted clusters as undone, changing their flag and removing them from adjusted_clusters_df.\n", + " \"\"\"\n", + " global df, adjusted_clusters_df\n", + " checked_ids = {cluster_id for checkbox, cluster_id in adjust_checkboxes if checkbox.value}\n", + " \n", + " if not checked_ids:\n", + " with selected_clusters_output:\n", + " display(HTML(\"Please select at least one cluster to set as undone.
\"))\n", + " return\n", + "\n", + " # Update 'flag_adjusted' to False for selected clusters\n", + " df.loc[df['current_cluster'].isin(checked_ids), 'flag_adjusted'] = False\n", + "\n", + " # Remove from adjusted_clusters_df\n", + " adjusted_clusters_df = adjusted_clusters_df[~adjusted_clusters_df['current_cluster'].isin(checked_ids)]\n", + "\n", + " # Refresh cluster display\n", + " display_clusters()\n", + "\n", + "\n", + "# Link the initial level widget to the update function\n", + "initial_level_widget.observe(update_initial_level, names='value')\n", + "\n", + "# Link the buttons to their functions\n", + "aggregate_button.on_click(aggregate_clusters_func)\n", + "split_button.on_click(split_clusters_func)\n", + "set_level_button.on_click(set_level_clusters_func)\n", + "done_button.on_click(done_adjusting_func)\n", + "start_adjust_button.on_click(start_adjustment)\n", + "# Link the toggle buttons to the appropriate function\n", + "view_adjusted_button.on_click(toggle_cluster_view)\n", + "view_clusters_to_adjust_button.on_click(toggle_cluster_view)\n", + "set_as_undone_button.on_click(set_clusters_undone)\n", + "\n", + "\n", + "\n", + "# Set initial current level and initialize DataFrame\n", + "current_level = initial_level_widget.value\n", + "initialize_df(current_level)\n", + "\n", + "# Arrange control widgets in one row\n", + "first_row_controls = widgets.HBox(\n", + " [\n", + " initial_level_widget,\n", + " start_adjust_button,\n", + " level_widget\n", + " ],\n", + " layout=widgets.Layout(margin='10px 0', justify_content='flex-start')\n", + ")\n", + "\n", + "# Arrange toggle buttons in a separate row\n", + "second_row_controls = widgets.HBox(\n", + " [\n", + " view_adjusted_button,\n", + " view_clusters_to_adjust_button\n", + " ],\n", + " layout=widgets.Layout(margin='10px 0', justify_content='flex-start')\n", + ")\n", + "\n", + "# Stack both rows vertically\n", + "control_widgets = widgets.VBox(\n", + " [\n", + " first_row_controls,\n", + " second_row_controls\n", + " ]\n", + ")\n", + "\n", + "\n", + "# Display the control widgets and initial clusters state\n", + "display(control_widgets)\n", + "display(selected_clusters_output)\n", + "display(clusters_output)\n", + "\n", + "# Initial display of clusters\n", + "display_clusters()" + ] + }, + { + "cell_type": "code", + "execution_count": 24, + "metadata": {}, + "outputs": [], + "source": [ + "# Choose the appropriate dataframe to display based on toggle\n", + "\n", + "# cclusters_df = df[df['flag_adjusted'] == False].copy()\n", + "\n", + "# # Group and sort as usual\n", + "# cclusters = cclusters_df.groupby(['current_cluster', 'current_cluster_name', 'current_level'])['question'].apply(list).reset_index()\n", + "# cclusters['question_count'] = cclusters['question'].apply(len)\n", + "# cclusters = cclusters.sort_values(by='question_count', ascending=False).reset_index(drop=True)\n", + "\n", + "\n", + "\n", + "# for index, row in clusters.iterrows():\n", + "# cluster_id = row['current_cluster']" + ] + }, + { + "cell_type": "code", + "execution_count": 25, + "metadata": {}, + "outputs": [], + "source": [ + "#cclusters\n" + ] + }, + { + "cell_type": "code", + "execution_count": 23, + "metadata": {}, + "outputs": [], + "source": [ + "#df.head(2)" + ] + }, + { + "cell_type": "code", + "execution_count": 22, + "metadata": {}, + "outputs": [], + "source": [ + "\n", + "#len(adjusted_clusters_df) \n", + "#df[df['flag_adjusted'] == True]\n", + "#add logic to if click on done remove from original dataframe, or flag so we know we adjusted these already - OK\n", + "#now adjust to have both view, one for showing the DF original and one for DF of adjusted - OK\n", + "#conseguir dar done em só um ou mais dos clusters que estão na seção de ajustes - OK\n", + "#conseguir dar um desfazer nos clusters que estão no done - OK\n", + "\n", + "#GOAL: Deixar tudo pronto para nuvemshop fazer o dever de casa deles\n", + "#output 1: PEerguntas feitas pelos clientes agrupadas por formas diferentes de fazer a mesma pergunta\n", + "#output 2: output1 + linkada ao conteúdo correto de resposta (gabarito).\n", + "#will be input for: Criar sessões com base em como clientes perguntas e resposta que deve ser dada\n", + "\n", + "#colocar em algum lugar que nuvemshop possa ter acesso para fazer o trabalho necessário de validação / ajuste\n", + "#adicionar os steps posteriores de conseguir selectionar entre as sessões já existentes qual responde\n", + "\n", + "#add extra infos sem separar mesmo.\n", + "#add the extracted_questions para ser visto se clicar no question, para ver mais no detalhe. Adicionar o ticket id também \n", + "\n", + "\n", + "#how should we do if we want to iterate on the adjusted DF? - create a new version\n", + "#Also allow the user to group clusters manually, and select\n", + "\n", + "#df.head(3)\n" + ] + } + ], + "metadata": { + "colab": { + "provenance": [] + }, + "kernelspec": { + "display_name": "test_env", + "language": "python", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.11.9" + } + }, + "nbformat": 4, + "nbformat_minor": 4 +} From c64776117a0976f2c1361f71fa88bd6974558dc1 Mon Sep 17 00:00:00 2001 From: felipeserrao <39130910+felipeserrao@users.noreply.github.com> Date: Mon, 14 Oct 2024 13:30:30 -0400 Subject: [PATCH 2/3] Rename index.ipynb to index_old.ipynb --- index.ipynb => index_old.ipynb | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename index.ipynb => index_old.ipynb (100%) diff --git a/index.ipynb b/index_old.ipynb similarity index 100% rename from index.ipynb rename to index_old.ipynb From 798948f35ff5b8f683075e78bef2c81ccb2311a6 Mon Sep 17 00:00:00 2001 From: felipeserrao <39130910+felipeserrao@users.noreply.github.com> Date: Mon, 14 Oct 2024 13:30:54 -0400 Subject: [PATCH 3/3] Rename Prototype Client Questions registry V2.ipynb to index.ipynb --- Prototype Client Questions registry V2.ipynb => index.ipynb | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename Prototype Client Questions registry V2.ipynb => index.ipynb (100%) diff --git a/Prototype Client Questions registry V2.ipynb b/index.ipynb similarity index 100% rename from Prototype Client Questions registry V2.ipynb rename to index.ipynb