We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
Add documentation for customizing visualization function output
### What is an issue?

Optuna's visualisation functions return editable objects. But it's not well documented. It would be good to have a description in [the visualization tutorial](https://optuna.readthedocs.io/en/stable/tutorial/10_key_features/005_visualization.html). (ref #4613)

--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `tutorial/10_key_features/005_visualization.py`
Content:
```
1 """
2 .. _visualization:
3 
4 Quick Visualization for Hyperparameter Optimization Analysis
5 ============================================================
6 
7 Optuna provides various visualization features in :mod:`optuna.visualization` to analyze optimization results visually.
8 
9 This tutorial walks you through this module by visualizing the history of lightgbm model for breast cancer dataset.
10 
11 For visualizing multi-objective optimization (i.e., the usage of :func:`optuna.visualization.plot_pareto_front`),
12 please refer to the tutorial of :ref:`multi_objective`.
13 
14 .. note::
15    By using `Optuna Dashboard <https://github.com/optuna/optuna-dashboard>`_, you can also check the optimization history,
16    hyperparameter importances, hyperparameter relationships, etc. in graphs and tables.
17    Please make your study persistent using :ref:`RDB backend <rdb>` and execute following commands to run Optuna Dashboard.
18 
19    .. code-block:: console
20 
21       $ pip install optuna-dashboard
22       $ optuna-dashboard sqlite:///example-study.db
23 
24    Please check out `the GitHub repository <https://github.com/optuna/optuna-dashboard>`_ for more details.
25 
26    .. list-table::
27       :header-rows: 1
28 
29       * - Manage Studies
30         - Visualize with Interactive Graphs
31       * - .. image:: https://user-images.githubusercontent.com/5564044/205545958-305f2354-c7cd-4687-be2f-9e46e7401838.gif
32         - .. image:: https://user-images.githubusercontent.com/5564044/205545965-278cd7f4-da7d-4e2e-ac31-6d81b106cada.gif
33 """
34 
35 ###################################################################################################
36 import lightgbm as lgb
37 import numpy as np
38 import sklearn.datasets
39 import sklearn.metrics
40 from sklearn.model_selection import train_test_split
41 
42 import optuna
43 
44 # You can use Matplotlib instead of Plotly for visualization by simply replacing `optuna.visualization` with
45 # `optuna.visualization.matplotlib` in the following examples.
46 from optuna.visualization import plot_contour
47 from optuna.visualization import plot_edf
48 from optuna.visualization import plot_intermediate_values
49 from optuna.visualization import plot_optimization_history
50 from optuna.visualization import plot_parallel_coordinate
51 from optuna.visualization import plot_param_importances
52 from optuna.visualization import plot_rank
53 from optuna.visualization import plot_slice
54 from optuna.visualization import plot_timeline
55 
56 SEED = 42
57 
58 np.random.seed(SEED)
59 
60 
61 ###################################################################################################
62 # Define the objective function.
63 def objective(trial):
64     data, target = sklearn.datasets.load_breast_cancer(return_X_y=True)
65     train_x, valid_x, train_y, valid_y = train_test_split(data, target, test_size=0.25)
66     dtrain = lgb.Dataset(train_x, label=train_y)
67     dvalid = lgb.Dataset(valid_x, label=valid_y)
68 
69     param = {
70         "objective": "binary",
71         "metric": "auc",
72         "verbosity": -1,
73         "boosting_type": "gbdt",
74         "bagging_fraction": trial.suggest_float("bagging_fraction", 0.4, 1.0),
75         "bagging_freq": trial.suggest_int("bagging_freq", 1, 7),
76         "min_child_samples": trial.suggest_int("min_child_samples", 5, 100),
77     }
78 
79     # Add a callback for pruning.
80     pruning_callback = optuna.integration.LightGBMPruningCallback(trial, "auc")
81     gbm = lgb.train(param, dtrain, valid_sets=[dvalid], callbacks=[pruning_callback])
82 
83     preds = gbm.predict(valid_x)
84     pred_labels = np.rint(preds)
85     accuracy = sklearn.metrics.accuracy_score(valid_y, pred_labels)
86     return accuracy
87 
88 
89 ###################################################################################################
90 study = optuna.create_study(
91     direction="maximize",
92     sampler=optuna.samplers.TPESampler(seed=SEED),
93     pruner=optuna.pruners.MedianPruner(n_warmup_steps=10),
94 )
95 study.optimize(objective, n_trials=100, timeout=600)
96 
97 ###################################################################################################
98 # Plot functions
99 # --------------
100 # Visualize the optimization history. See :func:`~optuna.visualization.plot_optimization_history` for the details.
101 plot_optimization_history(study)
102 
103 ###################################################################################################
104 # Visualize the learning curves of the trials. See :func:`~optuna.visualization.plot_intermediate_values` for the details.
105 plot_intermediate_values(study)
106 
107 ###################################################################################################
108 # Visualize high-dimensional parameter relationships. See :func:`~optuna.visualization.plot_parallel_coordinate` for the details.
109 plot_parallel_coordinate(study)
110 
111 ###################################################################################################
112 # Select parameters to visualize.
113 plot_parallel_coordinate(study, params=["bagging_freq", "bagging_fraction"])
114 
115 ###################################################################################################
116 # Visualize hyperparameter relationships. See :func:`~optuna.visualization.plot_contour` for the details.
117 plot_contour(study)
118 
119 ###################################################################################################
120 # Select parameters to visualize.
121 plot_contour(study, params=["bagging_freq", "bagging_fraction"])
122 
123 ###################################################################################################
124 # Visualize individual hyperparameters as slice plot. See :func:`~optuna.visualization.plot_slice` for the details.
125 plot_slice(study)
126 
127 ###################################################################################################
128 # Select parameters to visualize.
129 plot_slice(study, params=["bagging_freq", "bagging_fraction"])
130 
131 ###################################################################################################
132 # Visualize parameter importances. See :func:`~optuna.visualization.plot_param_importances` for the details.
133 plot_param_importances(study)
134 
135 ###################################################################################################
136 # Learn which hyperparameters are affecting the trial duration with hyperparameter importance.
137 optuna.visualization.plot_param_importances(
138     study, target=lambda t: t.duration.total_seconds(), target_name="duration"
139 )
140 
141 ###################################################################################################
142 # Visualize empirical distribution function. See :func:`~optuna.visualization.plot_edf` for the details.
143 plot_edf(study)
144 
145 ###################################################################################################
146 # Visualize parameter relations with scatter plots colored by objective values. See :func:`~optuna.visualization.plot_rank` for the details.
147 plot_rank(study)
148 
149 ###################################################################################################
150 # Visualize the optimization timeline of performed trials. See :func:`~optuna.visualization.plot_timeline` for the details.
151 plot_timeline(study)
152
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/tutorial/10_key_features/005_visualization.py b/tutorial/10_key_features/005_visualization.py
--- a/tutorial/10_key_features/005_visualization.py
+++ b/tutorial/10_key_features/005_visualization.py
@@ -149,3 +149,18 @@
 ###################################################################################################
 # Visualize the optimization timeline of performed trials. See :func:`~optuna.visualization.plot_timeline` for the details.
 plot_timeline(study)
+
+###################################################################################################
+# Customize generated figures
+# ---------------------------
+# In :mod:`optuna.visualization` and :mod:`optuna.visualization.matplotlib`, a function returns an editable figure object:
+# :class:`plotly.graph_objects.Figure` or :class:`matplotlib.axes.Axes` depending on the module.
+# This allows users to modify the generated figure for their demand by using API of the visualization library.
+# The following example replaces figure titles drawn by Plotly-based :func:`~optuna.visualization.plot_intermediate_values` manually.
+fig = plot_intermediate_values(study)
+
+fig.update_layout(
+    title="Hyperparameter optimization for GBDT-based binary classification",
+    xaxis_title="Iteration",
+    yaxis_title="Validation AUC",
+)

{"golden_diff": "diff --git a/tutorial/10_key_features/005_visualization.py b/tutorial/10_key_features/005_visualization.py\n--- a/tutorial/10_key_features/005_visualization.py\n+++ b/tutorial/10_key_features/005_visualization.py\n@@ -149,3 +149,18 @@\n ###################################################################################################\n # Visualize the optimization timeline of performed trials. See :func:`~optuna.visualization.plot_timeline` for the details.\n plot_timeline(study)\n+\n+###################################################################################################\n+# Customize generated figures\n+# ---------------------------\n+# In :mod:`optuna.visualization` and :mod:`optuna.visualization.matplotlib`, a function returns an editable figure object:\n+# :class:`plotly.graph_objects.Figure` or :class:`matplotlib.axes.Axes` depending on the module.\n+# This allows users to modify the generated figure for their demand by using API of the visualization library.\n+# The following example replaces figure titles drawn by Plotly-based :func:`~optuna.visualization.plot_intermediate_values` manually.\n+fig = plot_intermediate_values(study)\n+\n+fig.update_layout(\n+    title=\"Hyperparameter optimization for GBDT-based binary classification\",\n+    xaxis_title=\"Iteration\",\n+    yaxis_title=\"Validation AUC\",\n+)\n", "issue": "Add documentation for customizing visualization function output\n### What is an issue?\n\nOptuna's visualisation functions return editable objects. But it's not well documented. It would be good to have a description in [the visualization tutorial](https://optuna.readthedocs.io/en/stable/tutorial/10_key_features/005_visualization.html). (ref #4613)\n", "before_files": [{"content": "\"\"\"\n.. _visualization:\n\nQuick Visualization for Hyperparameter Optimization Analysis\n============================================================\n\nOptuna provides various visualization features in :mod:`optuna.visualization` to analyze optimization results visually.\n\nThis tutorial walks you through this module by visualizing the history of lightgbm model for breast cancer dataset.\n\nFor visualizing multi-objective optimization (i.e., the usage of :func:`optuna.visualization.plot_pareto_front`),\nplease refer to the tutorial of :ref:`multi_objective`.\n\n.. note::\n   By using `Optuna Dashboard <https://github.com/optuna/optuna-dashboard>`_, you can also check the optimization history,\n   hyperparameter importances, hyperparameter relationships, etc. in graphs and tables.\n   Please make your study persistent using :ref:`RDB backend <rdb>` and execute following commands to run Optuna Dashboard.\n\n   .. code-block:: console\n\n      $ pip install optuna-dashboard\n      $ optuna-dashboard sqlite:///example-study.db\n\n   Please check out `the GitHub repository <https://github.com/optuna/optuna-dashboard>`_ for more details.\n\n   .. list-table::\n      :header-rows: 1\n\n      * - Manage Studies\n        - Visualize with Interactive Graphs\n      * - .. image:: https://user-images.githubusercontent.com/5564044/205545958-305f2354-c7cd-4687-be2f-9e46e7401838.gif\n        - .. image:: https://user-images.githubusercontent.com/5564044/205545965-278cd7f4-da7d-4e2e-ac31-6d81b106cada.gif\n\"\"\"\n\n###################################################################################################\nimport lightgbm as lgb\nimport numpy as np\nimport sklearn.datasets\nimport sklearn.metrics\nfrom sklearn.model_selection import train_test_split\n\nimport optuna\n\n# You can use Matplotlib instead of Plotly for visualization by simply replacing `optuna.visualization` with\n# `optuna.visualization.matplotlib` in the following examples.\nfrom optuna.visualization import plot_contour\nfrom optuna.visualization import plot_edf\nfrom optuna.visualization import plot_intermediate_values\nfrom optuna.visualization import plot_optimization_history\nfrom optuna.visualization import plot_parallel_coordinate\nfrom optuna.visualization import plot_param_importances\nfrom optuna.visualization import plot_rank\nfrom optuna.visualization import plot_slice\nfrom optuna.visualization import plot_timeline\n\nSEED = 42\n\nnp.random.seed(SEED)\n\n\n###################################################################################################\n# Define the objective function.\ndef objective(trial):\n    data, target = sklearn.datasets.load_breast_cancer(return_X_y=True)\n    train_x, valid_x, train_y, valid_y = train_test_split(data, target, test_size=0.25)\n    dtrain = lgb.Dataset(train_x, label=train_y)\n    dvalid = lgb.Dataset(valid_x, label=valid_y)\n\n    param = {\n        \"objective\": \"binary\",\n        \"metric\": \"auc\",\n        \"verbosity\": -1,\n        \"boosting_type\": \"gbdt\",\n        \"bagging_fraction\": trial.suggest_float(\"bagging_fraction\", 0.4, 1.0),\n        \"bagging_freq\": trial.suggest_int(\"bagging_freq\", 1, 7),\n        \"min_child_samples\": trial.suggest_int(\"min_child_samples\", 5, 100),\n    }\n\n    # Add a callback for pruning.\n    pruning_callback = optuna.integration.LightGBMPruningCallback(trial, \"auc\")\n    gbm = lgb.train(param, dtrain, valid_sets=[dvalid], callbacks=[pruning_callback])\n\n    preds = gbm.predict(valid_x)\n    pred_labels = np.rint(preds)\n    accuracy = sklearn.metrics.accuracy_score(valid_y, pred_labels)\n    return accuracy\n\n\n###################################################################################################\nstudy = optuna.create_study(\n    direction=\"maximize\",\n    sampler=optuna.samplers.TPESampler(seed=SEED),\n    pruner=optuna.pruners.MedianPruner(n_warmup_steps=10),\n)\nstudy.optimize(objective, n_trials=100, timeout=600)\n\n###################################################################################################\n# Plot functions\n# --------------\n# Visualize the optimization history. See :func:`~optuna.visualization.plot_optimization_history` for the details.\nplot_optimization_history(study)\n\n###################################################################################################\n# Visualize the learning curves of the trials. See :func:`~optuna.visualization.plot_intermediate_values` for the details.\nplot_intermediate_values(study)\n\n###################################################################################################\n# Visualize high-dimensional parameter relationships. See :func:`~optuna.visualization.plot_parallel_coordinate` for the details.\nplot_parallel_coordinate(study)\n\n###################################################################################################\n# Select parameters to visualize.\nplot_parallel_coordinate(study, params=[\"bagging_freq\", \"bagging_fraction\"])\n\n###################################################################################################\n# Visualize hyperparameter relationships. See :func:`~optuna.visualization.plot_contour` for the details.\nplot_contour(study)\n\n###################################################################################################\n# Select parameters to visualize.\nplot_contour(study, params=[\"bagging_freq\", \"bagging_fraction\"])\n\n###################################################################################################\n# Visualize individual hyperparameters as slice plot. See :func:`~optuna.visualization.plot_slice` for the details.\nplot_slice(study)\n\n###################################################################################################\n# Select parameters to visualize.\nplot_slice(study, params=[\"bagging_freq\", \"bagging_fraction\"])\n\n###################################################################################################\n# Visualize parameter importances. See :func:`~optuna.visualization.plot_param_importances` for the details.\nplot_param_importances(study)\n\n###################################################################################################\n# Learn which hyperparameters are affecting the trial duration with hyperparameter importance.\noptuna.visualization.plot_param_importances(\n    study, target=lambda t: t.duration.total_seconds(), target_name=\"duration\"\n)\n\n###################################################################################################\n# Visualize empirical distribution function. See :func:`~optuna.visualization.plot_edf` for the details.\nplot_edf(study)\n\n###################################################################################################\n# Visualize parameter relations with scatter plots colored by objective values. See :func:`~optuna.visualization.plot_rank` for the details.\nplot_rank(study)\n\n###################################################################################################\n# Visualize the optimization timeline of performed trials. See :func:`~optuna.visualization.plot_timeline` for the details.\nplot_timeline(study)\n", "path": "tutorial/10_key_features/005_visualization.py"}], "after_files": [{"content": "\"\"\"\n.. _visualization:\n\nQuick Visualization for Hyperparameter Optimization Analysis\n============================================================\n\nOptuna provides various visualization features in :mod:`optuna.visualization` to analyze optimization results visually.\n\nThis tutorial walks you through this module by visualizing the history of lightgbm model for breast cancer dataset.\n\nFor visualizing multi-objective optimization (i.e., the usage of :func:`optuna.visualization.plot_pareto_front`),\nplease refer to the tutorial of :ref:`multi_objective`.\n\n.. note::\n   By using `Optuna Dashboard <https://github.com/optuna/optuna-dashboard>`_, you can also check the optimization history,\n   hyperparameter importances, hyperparameter relationships, etc. in graphs and tables.\n   Please make your study persistent using :ref:`RDB backend <rdb>` and execute following commands to run Optuna Dashboard.\n\n   .. code-block:: console\n\n      $ pip install optuna-dashboard\n      $ optuna-dashboard sqlite:///example-study.db\n\n   Please check out `the GitHub repository <https://github.com/optuna/optuna-dashboard>`_ for more details.\n\n   .. list-table::\n      :header-rows: 1\n\n      * - Manage Studies\n        - Visualize with Interactive Graphs\n      * - .. image:: https://user-images.githubusercontent.com/5564044/205545958-305f2354-c7cd-4687-be2f-9e46e7401838.gif\n        - .. image:: https://user-images.githubusercontent.com/5564044/205545965-278cd7f4-da7d-4e2e-ac31-6d81b106cada.gif\n\"\"\"\n\n###################################################################################################\nimport lightgbm as lgb\nimport numpy as np\nimport sklearn.datasets\nimport sklearn.metrics\nfrom sklearn.model_selection import train_test_split\n\nimport optuna\n\n# You can use Matplotlib instead of Plotly for visualization by simply replacing `optuna.visualization` with\n# `optuna.visualization.matplotlib` in the following examples.\nfrom optuna.visualization import plot_contour\nfrom optuna.visualization import plot_edf\nfrom optuna.visualization import plot_intermediate_values\nfrom optuna.visualization import plot_optimization_history\nfrom optuna.visualization import plot_parallel_coordinate\nfrom optuna.visualization import plot_param_importances\nfrom optuna.visualization import plot_rank\nfrom optuna.visualization import plot_slice\nfrom optuna.visualization import plot_timeline\n\nSEED = 42\n\nnp.random.seed(SEED)\n\n\n###################################################################################################\n# Define the objective function.\ndef objective(trial):\n    data, target = sklearn.datasets.load_breast_cancer(return_X_y=True)\n    train_x, valid_x, train_y, valid_y = train_test_split(data, target, test_size=0.25)\n    dtrain = lgb.Dataset(train_x, label=train_y)\n    dvalid = lgb.Dataset(valid_x, label=valid_y)\n\n    param = {\n        \"objective\": \"binary\",\n        \"metric\": \"auc\",\n        \"verbosity\": -1,\n        \"boosting_type\": \"gbdt\",\n        \"bagging_fraction\": trial.suggest_float(\"bagging_fraction\", 0.4, 1.0),\n        \"bagging_freq\": trial.suggest_int(\"bagging_freq\", 1, 7),\n        \"min_child_samples\": trial.suggest_int(\"min_child_samples\", 5, 100),\n    }\n\n    # Add a callback for pruning.\n    pruning_callback = optuna.integration.LightGBMPruningCallback(trial, \"auc\")\n    gbm = lgb.train(param, dtrain, valid_sets=[dvalid], callbacks=[pruning_callback])\n\n    preds = gbm.predict(valid_x)\n    pred_labels = np.rint(preds)\n    accuracy = sklearn.metrics.accuracy_score(valid_y, pred_labels)\n    return accuracy\n\n\n###################################################################################################\nstudy = optuna.create_study(\n    direction=\"maximize\",\n    sampler=optuna.samplers.TPESampler(seed=SEED),\n    pruner=optuna.pruners.MedianPruner(n_warmup_steps=10),\n)\nstudy.optimize(objective, n_trials=100, timeout=600)\n\n###################################################################################################\n# Plot functions\n# --------------\n# Visualize the optimization history. See :func:`~optuna.visualization.plot_optimization_history` for the details.\nplot_optimization_history(study)\n\n###################################################################################################\n# Visualize the learning curves of the trials. See :func:`~optuna.visualization.plot_intermediate_values` for the details.\nplot_intermediate_values(study)\n\n###################################################################################################\n# Visualize high-dimensional parameter relationships. See :func:`~optuna.visualization.plot_parallel_coordinate` for the details.\nplot_parallel_coordinate(study)\n\n###################################################################################################\n# Select parameters to visualize.\nplot_parallel_coordinate(study, params=[\"bagging_freq\", \"bagging_fraction\"])\n\n###################################################################################################\n# Visualize hyperparameter relationships. See :func:`~optuna.visualization.plot_contour` for the details.\nplot_contour(study)\n\n###################################################################################################\n# Select parameters to visualize.\nplot_contour(study, params=[\"bagging_freq\", \"bagging_fraction\"])\n\n###################################################################################################\n# Visualize individual hyperparameters as slice plot. See :func:`~optuna.visualization.plot_slice` for the details.\nplot_slice(study)\n\n###################################################################################################\n# Select parameters to visualize.\nplot_slice(study, params=[\"bagging_freq\", \"bagging_fraction\"])\n\n###################################################################################################\n# Visualize parameter importances. See :func:`~optuna.visualization.plot_param_importances` for the details.\nplot_param_importances(study)\n\n###################################################################################################\n# Learn which hyperparameters are affecting the trial duration with hyperparameter importance.\noptuna.visualization.plot_param_importances(\n    study, target=lambda t: t.duration.total_seconds(), target_name=\"duration\"\n)\n\n###################################################################################################\n# Visualize empirical distribution function. See :func:`~optuna.visualization.plot_edf` for the details.\nplot_edf(study)\n\n###################################################################################################\n# Visualize parameter relations with scatter plots colored by objective values. See :func:`~optuna.visualization.plot_rank` for the details.\nplot_rank(study)\n\n###################################################################################################\n# Visualize the optimization timeline of performed trials. See :func:`~optuna.visualization.plot_timeline` for the details.\nplot_timeline(study)\n\n###################################################################################################\n# Customize generated figures\n# ---------------------------\n# In :mod:`optuna.visualization` and :mod:`optuna.visualization.matplotlib`, a function returns an editable figure object:\n# :class:`plotly.graph_objects.Figure` or :class:`matplotlib.axes.Axes` depending on the module.\n# This allows users to modify the generated figure for their demand by using API of the visualization library.\n# The following example replaces figure titles drawn by Plotly-based :func:`~optuna.visualization.plot_intermediate_values` manually.\nfig = plot_intermediate_values(study)\n\nfig.update_layout(\n    title=\"Hyperparameter optimization for GBDT-based binary classification\",\n    xaxis_title=\"Iteration\",\n    yaxis_title=\"Validation AUC\",\n)\n", "path": "tutorial/10_key_features/005_visualization.py"}]}