Skip to content

Commit 3eceba7

Browse files
Circle CICircle CI
authored andcommitted
CircleCI update of dev docs (3374).
1 parent ad7d40a commit 3eceba7

File tree

794 files changed

+1540809
-1517500
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

794 files changed

+1540809
-1517500
lines changed

_downloads/006964755fe89c4eeb7c8b8016e96890/plot_otda_semi_supervised.py

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,9 @@
44
OTDA unsupervised vs semi-supervised setting
55
============================================
66
7+
.. note::
8+
Example added in release: 0.1.9.
9+
710
This example introduces a semi supervised domain adaptation in a 2D setting.
811
It explicit the problem of semi supervised domain adaptation and introduces
912
some optimal transport approaches to solve it.
@@ -107,13 +110,13 @@
107110
pl.figure(2, figsize=(8, 4))
108111

109112
pl.subplot(1, 2, 1)
110-
pl.imshow(ot_sinkhorn_un.coupling_, interpolation="nearest")
113+
pl.imshow(ot_sinkhorn_un.coupling_, interpolation="nearest", cmap="gray_r")
111114
pl.xticks([])
112115
pl.yticks([])
113116
pl.title("Optimal coupling\nUnsupervised DA")
114117

115118
pl.subplot(1, 2, 2)
116-
pl.imshow(ot_sinkhorn_semi.coupling_, interpolation="nearest")
119+
pl.imshow(ot_sinkhorn_semi.coupling_, interpolation="nearest", cmap="gray_r")
117120
pl.xticks([])
118121
pl.yticks([])
119122
pl.title("Optimal coupling\nSemi-supervised DA")
Lines changed: 187 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,187 @@
1+
{
2+
"cells": [
3+
{
4+
"cell_type": "markdown",
5+
"metadata": {},
6+
"source": [
7+
"\n# Low rank Gromov-Wasterstein between samples\n\n<div class=\"alert alert-info\"><h4>Note</h4><p>Example added in release: 0.9.4.</p></div>\n\nComparison between entropic Gromov-Wasserstein and Low Rank Gromov Wasserstein [67]\non two curves in 2D and 3D, both sampled with 200 points.\n\nThe squared Euclidean distance is considered as the ground cost for both samples.\n\n[67] Scetbon, M., Peyr\u00e9, G. & Cuturi, M. (2022).\n\"Linear-Time GromovWasserstein Distances using Low Rank Couplings and Costs\".\nIn International Conference on Machine Learning (ICML), 2022.\n"
8+
]
9+
},
10+
{
11+
"cell_type": "code",
12+
"execution_count": null,
13+
"metadata": {
14+
"collapsed": false
15+
},
16+
"outputs": [],
17+
"source": [
18+
"# Author: Laur\u00e8ne David <[email protected]>\n#\n# License: MIT License\n#\n# sphinx_gallery_thumbnail_number = 3"
19+
]
20+
},
21+
{
22+
"cell_type": "code",
23+
"execution_count": null,
24+
"metadata": {
25+
"collapsed": false
26+
},
27+
"outputs": [],
28+
"source": [
29+
"import numpy as np\nimport matplotlib.pylab as pl\nimport ot.plot\nimport time"
30+
]
31+
},
32+
{
33+
"cell_type": "markdown",
34+
"metadata": {},
35+
"source": [
36+
"## Generate data\n\n"
37+
]
38+
},
39+
{
40+
"cell_type": "code",
41+
"execution_count": null,
42+
"metadata": {
43+
"collapsed": false
44+
},
45+
"outputs": [],
46+
"source": [
47+
"n_samples = 200\n\n# Generate 2D and 3D curves\ntheta = np.linspace(-4 * np.pi, 4 * np.pi, n_samples)\nz = np.linspace(1, 2, n_samples)\nr = z**2 + 1\nx = r * np.sin(theta)\ny = r * np.cos(theta)\n\n# Source and target distribution\nX = np.concatenate([x.reshape(-1, 1), z.reshape(-1, 1)], axis=1)\nY = np.concatenate([x.reshape(-1, 1), y.reshape(-1, 1), z.reshape(-1, 1)], axis=1)"
48+
]
49+
},
50+
{
51+
"cell_type": "markdown",
52+
"metadata": {},
53+
"source": [
54+
"## Plot data\n\n"
55+
]
56+
},
57+
{
58+
"cell_type": "markdown",
59+
"metadata": {},
60+
"source": [
61+
"Plot the source and target samples\n\n"
62+
]
63+
},
64+
{
65+
"cell_type": "code",
66+
"execution_count": null,
67+
"metadata": {
68+
"collapsed": false
69+
},
70+
"outputs": [],
71+
"source": [
72+
"fig = pl.figure(1, figsize=(10, 4))\n\nax = fig.add_subplot(121)\nax.plot(X[:, 0], X[:, 1], color=\"blue\", linewidth=6)\nax.tick_params(\n left=False, right=False, labelleft=False, labelbottom=False, bottom=False\n)\nax.set_title(\"2D curve (source)\")\n\nax2 = fig.add_subplot(122, projection=\"3d\")\nax2.plot(Y[:, 0], Y[:, 1], Y[:, 2], c=\"red\", linewidth=6)\nax2.tick_params(\n left=False, right=False, labelleft=False, labelbottom=False, bottom=False\n)\nax2.view_init(15, -50)\nax2.set_title(\"3D curve (target)\")\n\npl.tight_layout()\npl.show()"
73+
]
74+
},
75+
{
76+
"cell_type": "markdown",
77+
"metadata": {},
78+
"source": [
79+
"## Entropic Gromov-Wasserstein\n\n"
80+
]
81+
},
82+
{
83+
"cell_type": "code",
84+
"execution_count": null,
85+
"metadata": {
86+
"collapsed": false
87+
},
88+
"outputs": [],
89+
"source": [
90+
"# Compute cost matrices\nC1 = ot.dist(X, X, metric=\"sqeuclidean\")\nC2 = ot.dist(Y, Y, metric=\"sqeuclidean\")\n\n# Scale cost matrices\nr1 = C1.max()\nr2 = C2.max()\n\nC1 = C1 / r1\nC2 = C2 / r2\n\n\n# Solve entropic gw\nreg = 5 * 1e-3\n\nstart = time.time()\ngw, log = ot.gromov.entropic_gromov_wasserstein(\n C1, C2, tol=1e-3, epsilon=reg, log=True, verbose=False\n)\n\nend = time.time()\ntime_entropic = end - start\n\nentropic_gw_loss = np.round(log[\"gw_dist\"], 3)\n\n# Plot entropic gw\npl.figure(2)\npl.imshow(gw, interpolation=\"nearest\", aspect=\"auto\", cmap=\"gray_r\")\npl.title(\"Entropic Gromov-Wasserstein (loss={})\".format(entropic_gw_loss))\npl.show()"
91+
]
92+
},
93+
{
94+
"cell_type": "markdown",
95+
"metadata": {},
96+
"source": [
97+
"## Low rank squared euclidean cost matrices\n%%\n\n"
98+
]
99+
},
100+
{
101+
"cell_type": "code",
102+
"execution_count": null,
103+
"metadata": {
104+
"collapsed": false
105+
},
106+
"outputs": [],
107+
"source": [
108+
"# Compute the low rank sqeuclidean cost decompositions\nA1, A2 = ot.lowrank.compute_lr_sqeuclidean_matrix(X, X, rescale_cost=False)\nB1, B2 = ot.lowrank.compute_lr_sqeuclidean_matrix(Y, Y, rescale_cost=False)\n\n# Scale the low rank cost matrices\nA1, A2 = A1 / np.sqrt(r1), A2 / np.sqrt(r1)\nB1, B2 = B1 / np.sqrt(r2), B2 / np.sqrt(r2)"
109+
]
110+
},
111+
{
112+
"cell_type": "markdown",
113+
"metadata": {},
114+
"source": [
115+
"## Low rank Gromov-Wasserstein\n%%\n\n"
116+
]
117+
},
118+
{
119+
"cell_type": "code",
120+
"execution_count": null,
121+
"metadata": {
122+
"collapsed": false
123+
},
124+
"outputs": [],
125+
"source": [
126+
"# Solve low rank gromov-wasserstein with different ranks\nlist_rank = [10, 50]\nlist_P_GW = []\nlist_loss_GW = []\nlist_time_GW = []\n\nfor rank in list_rank:\n start = time.time()\n\n Q, R, g, log = ot.lowrank_gromov_wasserstein_samples(\n X,\n Y,\n reg=0,\n rank=rank,\n rescale_cost=False,\n cost_factorized_Xs=(A1, A2),\n cost_factorized_Xt=(B1, B2),\n seed_init=49,\n numItermax=1000,\n log=True,\n stopThr=1e-6,\n )\n end = time.time()\n\n P = log[\"lazy_plan\"][:]\n loss = log[\"value\"]\n\n list_P_GW.append(P)\n list_loss_GW.append(np.round(loss, 3))\n list_time_GW.append(end - start)"
127+
]
128+
},
129+
{
130+
"cell_type": "markdown",
131+
"metadata": {},
132+
"source": [
133+
"Plot low rank GW with different ranks\n\n"
134+
]
135+
},
136+
{
137+
"cell_type": "code",
138+
"execution_count": null,
139+
"metadata": {
140+
"collapsed": false
141+
},
142+
"outputs": [],
143+
"source": [
144+
"pl.figure(3, figsize=(10, 4))\n\npl.subplot(1, 2, 1)\npl.imshow(list_P_GW[0], interpolation=\"nearest\", aspect=\"auto\", cmap=\"gray_r\")\npl.title(\"Low rank GW (rank=10, loss={})\".format(list_loss_GW[0]))\n\npl.subplot(1, 2, 2)\npl.imshow(list_P_GW[1], interpolation=\"nearest\", aspect=\"auto\", cmap=\"gray_r\")\npl.title(\"Low rank GW (rank=50, loss={})\".format(list_loss_GW[1]))\n\npl.tight_layout()\npl.show()"
145+
]
146+
},
147+
{
148+
"cell_type": "markdown",
149+
"metadata": {},
150+
"source": [
151+
"Compare computation time between entropic GW and low rank GW\n\n"
152+
]
153+
},
154+
{
155+
"cell_type": "code",
156+
"execution_count": null,
157+
"metadata": {
158+
"collapsed": false
159+
},
160+
"outputs": [],
161+
"source": [
162+
"print(\"Entropic GW: {:.2f}s\".format(time_entropic))\nprint(\"Low rank GW (rank=10): {:.2f}s\".format(list_time_GW[0]))\nprint(\"Low rank GW (rank=50): {:.2f}s\".format(list_time_GW[1]))"
163+
]
164+
}
165+
],
166+
"metadata": {
167+
"kernelspec": {
168+
"display_name": "Python 3",
169+
"language": "python",
170+
"name": "python3"
171+
},
172+
"language_info": {
173+
"codemirror_mode": {
174+
"name": "ipython",
175+
"version": 3
176+
},
177+
"file_extension": ".py",
178+
"mimetype": "text/x-python",
179+
"name": "python",
180+
"nbconvert_exporter": "python",
181+
"pygments_lexer": "ipython3",
182+
"version": "3.10.18"
183+
}
184+
},
185+
"nbformat": 4,
186+
"nbformat_minor": 0
187+
}
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
{
2+
"cells": [
3+
{
4+
"cell_type": "markdown",
5+
"metadata": {},
6+
"source": [
7+
"\n# Partial Wasserstein in 1D\n\nThis script demonstrates how to compute and visualize the Partial Wasserstein distance between two 1D discrete distributions using `ot.partial.partial_wasserstein_1d`.\n\nWe illustrate the intermediate transport plans for all `k = 1...n`, where `n = min(len(x_a), len(x_b))`.\n"
8+
]
9+
},
10+
{
11+
"cell_type": "code",
12+
"execution_count": null,
13+
"metadata": {
14+
"collapsed": false
15+
},
16+
"outputs": [],
17+
"source": [
18+
"# sphinx_gallery_thumbnail_number = 5\n\nimport numpy as np\nimport matplotlib.pyplot as plt\nfrom ot.partial import partial_wasserstein_1d\n\n\ndef plot_partial_transport(\n ax, x_a, x_b, indices_a=None, indices_b=None, marginal_costs=None\n):\n y_a = np.ones_like(x_a)\n y_b = -np.ones_like(x_b)\n min_min = min(x_a.min(), x_b.min())\n max_max = max(x_a.max(), x_b.max())\n\n ax.plot([min_min - 1, max_max + 1], [1, 1], \"k-\", lw=0.5, alpha=0.5)\n ax.plot([min_min - 1, max_max + 1], [-1, -1], \"k-\", lw=0.5, alpha=0.5)\n\n # Plot transport lines\n if indices_a is not None and indices_b is not None:\n subset_a = np.sort(x_a[indices_a])\n subset_b = np.sort(x_b[indices_b])\n\n for x_a_i, x_b_j in zip(subset_a, subset_b):\n ax.plot([x_a_i, x_b_j], [1, -1], \"k--\", alpha=0.7)\n\n # Plot all points\n ax.plot(x_a, y_a, \"o\", color=\"C0\", label=\"x_a\", markersize=8)\n ax.plot(x_b, y_b, \"o\", color=\"C1\", label=\"x_b\", markersize=8)\n\n if marginal_costs is not None:\n k = len(marginal_costs)\n ax.set_title(\n f\"Partial Transport - k = {k}, Cumulative Cost = {sum(marginal_costs):.2f}\",\n fontsize=16,\n )\n else:\n ax.set_title(\"Original 1D Discrete Distributions\", fontsize=16)\n ax.legend(loc=\"upper right\", fontsize=14)\n ax.set_yticks([])\n ax.set_xticks([])\n ax.set_ylim(-2, 2)\n ax.set_xlim(min(x_a.min(), x_b.min()) - 1, max(x_a.max(), x_b.max()) + 1)\n ax.axis(\"off\")\n\n\n# Simulate two 1D discrete distributions\nnp.random.seed(0)\nn = 6\nx_a = np.sort(np.random.uniform(0, 10, size=n))\nx_b = np.sort(np.random.uniform(0, 10, size=n))\n\n# Plot original distributions\nplt.figure(figsize=(6, 2))\nplot_partial_transport(plt.gca(), x_a, x_b)\nplt.show()"
19+
]
20+
},
21+
{
22+
"cell_type": "code",
23+
"execution_count": null,
24+
"metadata": {
25+
"collapsed": false
26+
},
27+
"outputs": [],
28+
"source": [
29+
"indices_a, indices_b, marginal_costs = partial_wasserstein_1d(x_a, x_b)\n\n# Compute cumulative cost\ncumulative_costs = np.cumsum(marginal_costs)\n\n# Visualize all partial transport plans\nfor k in range(n):\n plt.figure(figsize=(6, 2))\n plot_partial_transport(\n plt.gca(),\n x_a,\n x_b,\n indices_a[: k + 1],\n indices_b[: k + 1],\n marginal_costs[: k + 1],\n )\n plt.show()"
30+
]
31+
}
32+
],
33+
"metadata": {
34+
"kernelspec": {
35+
"display_name": "Python 3",
36+
"language": "python",
37+
"name": "python3"
38+
},
39+
"language_info": {
40+
"codemirror_mode": {
41+
"name": "ipython",
42+
"version": 3
43+
},
44+
"file_extension": ".py",
45+
"mimetype": "text/x-python",
46+
"name": "python",
47+
"nbconvert_exporter": "python",
48+
"pygments_lexer": "ipython3",
49+
"version": "3.10.18"
50+
}
51+
},
52+
"nbformat": 4,
53+
"nbformat_minor": 0
54+
}

_downloads/020b892b91e910d18254039df8f9f86e/plot_regpath.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,10 @@
33
================================================================
44
Regularization path of l2-penalized unbalanced optimal transport
55
================================================================
6+
7+
.. note::
8+
Example added in release: 0.8.0.
9+
610
This example illustrate the regularization path for 2D unbalanced
711
optimal transport. We present here both the fully relaxed case
812
and the semi-relaxed case.

_downloads/059a63fc6cb655dcd2f1c9a61bb9d7ec/plot_OT_2D_samples.ipynb

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
"cell_type": "markdown",
55
"metadata": {},
66
"source": [
7-
"\n# Optimal Transport between 2D empirical distributions\n\nIllustration of 2D optimal transport between distributions that are weighted\nsum of Diracs. The OT matrix is plotted with the samples.\n"
7+
"\n# Optimal Transport between empirical distributions\n\nIllustration of optimal transport between distributions in 2D that are weighted\nsum of Diracs. The OT matrix is plotted with the samples.\n"
88
]
99
},
1010
{
@@ -51,7 +51,7 @@
5151
},
5252
"outputs": [],
5353
"source": [
54-
"pl.figure(1)\npl.plot(xs[:, 0], xs[:, 1], \"+b\", label=\"Source samples\")\npl.plot(xt[:, 0], xt[:, 1], \"xr\", label=\"Target samples\")\npl.legend(loc=0)\npl.title(\"Source and target distributions\")\n\npl.figure(2)\npl.imshow(M, interpolation=\"nearest\")\npl.title(\"Cost matrix M\")"
54+
"pl.figure(1)\npl.plot(xs[:, 0], xs[:, 1], \"+b\", label=\"Source samples\")\npl.plot(xt[:, 0], xt[:, 1], \"xr\", label=\"Target samples\")\npl.legend(loc=0)\npl.title(\"Source and target distributions\")\n\npl.figure(2)\npl.imshow(M, interpolation=\"nearest\", cmap=\"gray_r\")\npl.title(\"Cost matrix M\")"
5555
]
5656
},
5757
{
@@ -69,7 +69,7 @@
6969
},
7070
"outputs": [],
7171
"source": [
72-
"G0 = ot.emd(a, b, M)\n\npl.figure(3)\npl.imshow(G0, interpolation=\"nearest\")\npl.title(\"OT matrix G0\")\n\npl.figure(4)\not.plot.plot2D_samples_mat(xs, xt, G0, c=[0.5, 0.5, 1])\npl.plot(xs[:, 0], xs[:, 1], \"+b\", label=\"Source samples\")\npl.plot(xt[:, 0], xt[:, 1], \"xr\", label=\"Target samples\")\npl.legend(loc=0)\npl.title(\"OT matrix with samples\")"
72+
"G0 = ot.solve(M, a, b).plan\n\npl.figure(3)\npl.imshow(G0, interpolation=\"nearest\", cmap=\"gray_r\")\npl.title(\"OT matrix G0\")\n\npl.figure(4)\not.plot.plot2D_samples_mat(xs, xt, G0, c=[0.5, 0.5, 1])\npl.plot(xs[:, 0], xs[:, 1], \"+b\", label=\"Source samples\")\npl.plot(xt[:, 0], xt[:, 1], \"xr\", label=\"Target samples\")\npl.legend(loc=0)\npl.title(\"OT matrix with samples\")"
7373
]
7474
},
7575
{
@@ -87,7 +87,7 @@
8787
},
8888
"outputs": [],
8989
"source": [
90-
"# reg term\nlambd = 1e-1\n\nGs = ot.sinkhorn(a, b, M, lambd)\n\npl.figure(5)\npl.imshow(Gs, interpolation=\"nearest\")\npl.title(\"OT matrix sinkhorn\")\n\npl.figure(6)\not.plot.plot2D_samples_mat(xs, xt, Gs, color=[0.5, 0.5, 1])\npl.plot(xs[:, 0], xs[:, 1], \"+b\", label=\"Source samples\")\npl.plot(xt[:, 0], xt[:, 1], \"xr\", label=\"Target samples\")\npl.legend(loc=0)\npl.title(\"OT matrix Sinkhorn with samples\")\n\npl.show()"
90+
"# reg term\nlambd = 1e-1\n\nGs = ot.sinkhorn(a, b, M, lambd)\n\npl.figure(5)\npl.imshow(Gs, interpolation=\"nearest\", cmap=\"gray_r\")\npl.title(\"OT matrix sinkhorn\")\n\npl.figure(6)\not.plot.plot2D_samples_mat(xs, xt, Gs, color=[0.5, 0.5, 1])\npl.plot(xs[:, 0], xs[:, 1], \"+b\", label=\"Source samples\")\npl.plot(xt[:, 0], xt[:, 1], \"xr\", label=\"Target samples\")\npl.legend(loc=0)\npl.title(\"OT matrix Sinkhorn with samples\")\n\npl.show()"
9191
]
9292
},
9393
{
@@ -105,7 +105,7 @@
105105
},
106106
"outputs": [],
107107
"source": [
108-
"# reg term\nlambd = 1e-1\n\nGes = ot.bregman.empirical_sinkhorn(xs, xt, lambd)\n\npl.figure(7)\npl.imshow(Ges, interpolation=\"nearest\")\npl.title(\"OT matrix empirical sinkhorn\")\n\npl.figure(8)\not.plot.plot2D_samples_mat(xs, xt, Ges, color=[0.5, 0.5, 1])\npl.plot(xs[:, 0], xs[:, 1], \"+b\", label=\"Source samples\")\npl.plot(xt[:, 0], xt[:, 1], \"xr\", label=\"Target samples\")\npl.legend(loc=0)\npl.title(\"OT matrix Sinkhorn from samples\")\n\npl.show()"
108+
"# reg term\nlambd = 1e-1\n\nGes = ot.bregman.empirical_sinkhorn(xs, xt, lambd)\n\npl.figure(7)\npl.imshow(Ges, interpolation=\"nearest\", cmap=\"gray_r\")\npl.title(\"OT matrix empirical sinkhorn\")\n\npl.figure(8)\not.plot.plot2D_samples_mat(xs, xt, Ges, color=[0.5, 0.5, 1])\npl.plot(xs[:, 0], xs[:, 1], \"+b\", label=\"Source samples\")\npl.plot(xt[:, 0], xt[:, 1], \"xr\", label=\"Target samples\")\npl.legend(loc=0)\npl.title(\"OT matrix Sinkhorn from samples\")\n\npl.show()"
109109
]
110110
}
111111
],
@@ -125,7 +125,7 @@
125125
"name": "python",
126126
"nbconvert_exporter": "python",
127127
"pygments_lexer": "ipython3",
128-
"version": "3.10.15"
128+
"version": "3.10.18"
129129
}
130130
},
131131
"nbformat": 4,
Binary file not shown.

_downloads/0b94278a6426d6eb1fd193bf87be12cf/plot_otda_color_images.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,9 @@
44
OT for image color adaptation
55
=============================
66
7+
.. note::
8+
Example added in release: 0.1.9.
9+
710
This example presents a way of transferring colors between two images
811
with Optimal Transport as introduced in [6]
912

0 commit comments

Comments
 (0)