{"id":15065403,"url":"https://github.com/xl0/lovely-numpy","last_synced_at":"2025-04-09T21:15:35.015Z","repository":{"id":63362032,"uuid":"567265303","full_name":"xl0/lovely-numpy","owner":"xl0","description":"NumPy arrays, ready for human consumption","archived":false,"fork":false,"pushed_at":"2024-07-20T19:40:58.000Z","size":23607,"stargazers_count":68,"open_issues_count":3,"forks_count":4,"subscribers_count":3,"default_branch":"master","last_synced_at":"2025-04-09T21:15:21.288Z","etag":null,"topics":["deep-learning","library","numpy","statistics","visualization"],"latest_commit_sha":null,"homepage":"https://xl0.github.io/lovely-numpy","language":"Jupyter Notebook","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/xl0.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2022-11-17T12:32:39.000Z","updated_at":"2025-03-24T12:09:58.000Z","dependencies_parsed_at":"2024-01-17T01:35:51.146Z","dependency_job_id":"668b17da-55d1-4083-80b7-41e3914fa94d","html_url":"https://github.com/xl0/lovely-numpy","commit_stats":{"total_commits":66,"total_committers":2,"mean_commits":33.0,"dds":"0.030303030303030276","last_synced_commit":"8e834eb62d8fae4e2798c7551fdc8e11f4dea7fb"},"previous_names":[],"tags_count":10,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xl0%2Flovely-numpy","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xl0%2Flovely-numpy/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xl0%2Flovely-numpy/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xl0%2Flovely-numpy/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/xl0","download_url":"https://codeload.github.com/xl0/lovely-numpy/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248111973,"owners_count":21049578,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["deep-learning","library","numpy","statistics","visualization"],"created_at":"2024-09-25T00:37:58.297Z","updated_at":"2025-04-09T21:15:34.929Z","avatar_url":"https://github.com/xl0.png","language":"Jupyter Notebook","funding_links":[],"categories":[],"sub_categories":[],"readme":"💟 Lovely NumPy\n================\n\n\u003c!-- WARNING: THIS FILE WAS AUTOGENERATED! DO NOT EDIT! --\u003e\n\n\u003cdiv\u003e\n\n## [Read full docs](https://xl0.github.io/lovely-numpy)\n\n\u003c/div\u003e\n\n### More lovely stuff\n\n##### Working with numbers\n\n- [PyTorch](https://pytorch.org/): ❤️ [Lovely\n  Tensors](https://github.com/xl0/lovely-tensors)\n- [JAX](https://jax.readthedocs.io/): 💘 [Lovely\n  `JAX`](https://github.com/xl0/lovely-jax)\n- [TinyGrad](https://github.com/tinygrad/tinygrad): 🫀 [Lovely\n  Grad](https://github.com/xl0/lovely-grad)\n\n##### Proompting\n\n- Log prompts with 💌 [Lovely\n  Prompts](https://github.com/xl0/lovely-prompts)\n- Better LangChain: 😎 [Proompter](https://github.com/xl0/proompter)\n\n##### Community\n\n- [Discord](https://discord.gg/qBaqauUWXP)\n\n## Install\n\n``` sh\npip install lovely-numpy\n```\n\nor\n\n``` sh\nconda install -c conda-forge lovely-numpy\n```\n\n## How to use\n\nHow often do you find yourself debugging NumPy code? You dump your\nvariable to the cell output, and see this:\n\n``` python\nnumbers\n```\n\n    array([[[-0.3541, -0.1975, -0.6715],\n            [-0.3369, -0.1975, -0.9853],\n            ...,\n            [-0.4739, -0.3725, -0.689 ],\n            [ 2.2489,  2.4111,  2.396 ]],\n\n           [[-0.4054, -0.25  , -0.7238],\n            [-0.4226, -0.2325, -1.0724],\n            ...,\n            [-0.8507, -0.6702, -1.0201],\n            [ 2.1633,  2.3585,  2.3263]],\n\n           ...,\n\n           [[-0.8507, -0.3901, -1.1944],\n            [-0.7822, -0.2325, -1.4559],\n            ...,\n            [-1.5014, -1.2304, -1.4733],\n            [ 2.1804,  2.4111,  2.4308]],\n\n           [[-0.8335, -0.4076, -1.2293],\n            [-0.8164, -0.285 , -1.5256],\n            ...,\n            [-1.5528, -1.2829, -1.5256],\n            [ 2.1119,  2.341 ,  2.3611]]], dtype=float32)\n\nWas it really useful for you, as a human, to see all these numbers?\n\nWhat is the shape? The size?  \nWhat are the statistics?  \nAre any of the values `nan` or `inf`?  \nIs it an image of a man holding a tench?\n\n``` python\nfrom lovely_numpy import lo\n```\n\n## \u003ccode\u003eLo\u003c/code\u003e and behold!\n\n``` python\nlo(numbers)\n```\n\n    array[196, 196, 3] f32 n=115248 (0.4Mb) x∈[-2.118, 2.640] μ=-0.388 σ=1.073\n\nBetter, eh?\n\n``` python\nlo(numbers[1,:6,1]) # Still shows values if there are not too many.\n```\n\n    array[6] f32 x∈[-0.408, -0.232] μ=-0.340 σ=0.075 [-0.250, -0.232, -0.338, -0.408, -0.408, -0.408]\n\n``` python\nspicy = numbers[0,:12,0].copy()\n\nspicy[0] *= 10000\nspicy[1] /= 10000\nspicy[2] = float('inf')\nspicy[3] = float('-inf')\nspicy[4] = float('nan')\n\nspicy = spicy.reshape((2,6))\nlo(spicy) # Spicy stuff\n```\n\n    array[2, 6] f32 n=12 x∈[-3.541e+03, -3.369e-05] μ=-393.776 σ=1.113e+03 +Inf! -Inf! NaN!\n\n``` python\nlo(np.zeros((10, 10))) # A zero array - make it obvious\n```\n\n    array[10, 10] n=100 all_zeros\n\n``` python\nlo(spicy, verbose=True)\n```\n\n    array[2, 6] f32 n=12 x∈[-3.541e+03, -3.369e-05] μ=-393.776 σ=1.113e+03 +Inf! -Inf! NaN!\n    array([[-3540.5432,    -0.    , ...,        nan,    -0.4054],\n           [   -0.4226,    -0.4911, ...,    -0.5424,    -0.5082]],\n          dtype=float32)\n\n## Going `.deeper`\n\n``` python\nlo(numbers.transpose(2,1,0)).deeper\n```\n\n    array[3, 196, 196] f32 n=115248 (0.4Mb) x∈[-2.118, 2.640] μ=-0.388 σ=1.073\n      array[196, 196] f32 n=38416 x∈[-2.118, 2.249] μ=-0.324 σ=1.036\n      array[196, 196] f32 n=38416 x∈[-1.966, 2.429] μ=-0.274 σ=0.973\n      array[196, 196] f32 n=38416 x∈[-1.804, 2.640] μ=-0.567 σ=1.178\n\n``` python\n# You can go deeper if you need to\nlo(numbers[:3,:4]).deeper(2)\n```\n\n    array[3, 4, 3] f32 n=36 x∈[-1.125, -0.197] μ=-0.563 σ=0.280\n      array[4, 3] f32 n=12 x∈[-0.985, -0.197] μ=-0.487 σ=0.259\n        array[3] f32 x∈[-0.672, -0.197] μ=-0.408 σ=0.197 [-0.354, -0.197, -0.672]\n        array[3] f32 x∈[-0.985, -0.197] μ=-0.507 σ=0.343 [-0.337, -0.197, -0.985]\n        array[3] f32 x∈[-0.881, -0.303] μ=-0.530 σ=0.252 [-0.405, -0.303, -0.881]\n        array[3] f32 x∈[-0.776, -0.303] μ=-0.506 σ=0.199 [-0.440, -0.303, -0.776]\n      array[4, 3] f32 n=12 x∈[-1.072, -0.232] μ=-0.571 σ=0.281\n        array[3] f32 x∈[-0.724, -0.250] μ=-0.460 σ=0.197 [-0.405, -0.250, -0.724]\n        array[3] f32 x∈[-1.072, -0.232] μ=-0.576 σ=0.360 [-0.423, -0.232, -1.072]\n        array[3] f32 x∈[-0.968, -0.338] μ=-0.599 σ=0.268 [-0.491, -0.338, -0.968]\n        array[3] f32 x∈[-0.968, -0.408] μ=-0.651 σ=0.235 [-0.577, -0.408, -0.968]\n      array[4, 3] f32 n=12 x∈[-1.125, -0.285] μ=-0.631 σ=0.280\n        array[3] f32 x∈[-0.828, -0.303] μ=-0.535 σ=0.219 [-0.474, -0.303, -0.828]\n        array[3] f32 x∈[-1.125, -0.285] μ=-0.628 σ=0.360 [-0.474, -0.285, -1.125]\n        array[3] f32 x∈[-1.020, -0.390] μ=-0.651 σ=0.268 [-0.542, -0.390, -1.020]\n        array[3] f32 x∈[-1.003, -0.478] μ=-0.708 σ=0.219 [-0.645, -0.478, -1.003]\n\n## Now in `.rgb` color\n\nThe important queston - is it our man?\n\n``` python\nlo(numbers).rgb\n```\n\n![](index_files/figure-commonmark/cell-11-output-1.png)\n\n*Maaaaybe?* Looks like someone normalized him.\n\n``` python\nin_stats = ( (0.485, 0.456, 0.406),     # mean\n             (0.229, 0.224, 0.225) )    # std\n\n# numbers.rgb(in_stats, cl=True) # For channel-last input format\nlo(numbers).rgb(denorm=in_stats)\n```\n\n![](index_files/figure-commonmark/cell-12-output-1.png)\n\nIt’s indeed our hero, the Tenchman!\n\n## See the `.chans`\n\n``` python\n# .chans will map values betwen [-1,1] to colors.\n# Make our values fit into that range to avoid clipping.\nmean = np.array(in_stats[0])\nstd = np.array(in_stats[1])\nnumbers_01 = (numbers*std + mean).clip(0,1)\nlo(numbers_01)\n```\n\n    array[196, 196, 3] n=115248 (0.9Mb) x∈[0., 1.000] μ=0.361 σ=0.248\n\n``` python\nlo(numbers_01).chans\n```\n\n![](index_files/figure-commonmark/cell-14-output-1.png)\n\n## Grouping\n\n``` python\n# Make 8 images with progressively higher brightness and stack them 2x2x2.\neight_images = (np.stack([numbers]*8) + np.linspace(-2, 2, 8)[:,None,None,None])\neight_images = (eight_images\n                     *np.array(in_stats[1])\n                     +np.array(in_stats[0])\n                ).clip(0,1).reshape(2,2,2,196,196,3)\n\nlo(eight_images)\n```\n\n    array[2, 2, 2, 196, 196, 3] n=921984 (7.0Mb) x∈[0., 1.000] μ=0.382 σ=0.319\n\n``` python\nlo(eight_images).rgb\n```\n\n![](index_files/figure-commonmark/cell-16-output-1.png)\n\n## Histogram\n\n``` python\nlo(numbers+3).plt\n```\n\n![](index_files/figure-commonmark/cell-17-output-1.svg)\n\n``` python\nlo(numbers+3).plt(center=\"mean\", max_s=1000)\n```\n\n![](index_files/figure-commonmark/cell-18-output-1.svg)\n\n``` python\nlo(numbers+3).plt(center=\"range\")\n```\n\n![](index_files/figure-commonmark/cell-19-output-1.svg)\n\n## Options \\| [Docs](03d_utils.config.html)\n\n``` python\nfrom lovely_numpy import set_config, config, lovely\n```\n\n``` python\nset_config(precision=5, sci_mode=True, color=False)\nlo(np.array([1.,2,np.nan]))\n```\n\n    array[3] μ=1.50000e+00 σ=5.00000e-01 NaN! [1.00000e+00, 2.00000e+00, nan]\n\n``` python\nset_config(precision=None, sci_mode=None, color=None) # None -\u003e Reset to defaults\nlo(np.array([1.,2,np.nan]))\n```\n\n    array[3] μ=1.500 σ=0.500 NaN! [1.000, 2.000, nan]\n\n``` python\n# Or with config context manager.\nwith config(sci_mode=True):\n    print(lo(np.array([1,2,3])))\n\nprint(lo(np.array([1,2,3])))\n```\n\n    array[3] i64 x∈[1, 3] μ=2.000e+00 σ=8.165e-01 [1, 2, 3]\n    array[3] i64 x∈[1, 3] μ=2.000 σ=0.816 [1, 2, 3]\n\n## Without \u003ccode\u003eLo\u003c/code\u003e\n\n``` python\nfrom lovely_numpy import rgb, chans, plot\n```\n\n``` python\nlovely(numbers) # Returns `str`, that's why you see ''.\n# Note:  lo(x) returns a wrapper object with a `__repr__` and other methods.\n```\n\n    'array[196, 196, 3] f32 n=115248 (0.4Mb) x∈[-2.118, 2.640] μ=-0.388 σ=1.073'\n\n``` python\nrgb(numbers, denorm=in_stats)\n```\n\n![](index_files/figure-commonmark/cell-26-output-1.png)\n\n``` python\nchans(numbers*0.3+0.5)\n```\n\n![](index_files/figure-commonmark/cell-27-output-1.png)\n\n``` python\nplot(numbers)\n```\n\n![](index_files/figure-commonmark/cell-28-output-1.svg)\n\n## Matplotlib integration \\| [Docs](matplotlib.html)\n\n``` python\nlo(numbers).rgb(in_stats).fig # matplotlib figure\n```\n\n![](index_files/figure-commonmark/cell-29-output-1.png)\n\n``` python\nlo(numbers).plt.fig.savefig('pretty.svg') # Save it\n```\n\n``` python\n!file pretty.svg; rm pretty.svg\n```\n\n    pretty.svg: SVG Scalable Vector Graphics image\n\n``` python\nfig = plt.figure(figsize=(8,3))\nfig.set_constrained_layout(True)\ngs = fig.add_gridspec(2,2)\nax1 = fig.add_subplot(gs[0, :])\nax2 = fig.add_subplot(gs[1, 0])\nax3 = fig.add_subplot(gs[1,1:])\n\nax2.set_axis_off()\nax3.set_axis_off()\n\nlo(numbers_01).plt(ax=ax1)\nlo(numbers_01).rgb(ax=ax2)\nlo(numbers_01).chans(ax=ax3);\n```\n\n![](index_files/figure-commonmark/cell-32-output-1.png)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fxl0%2Flovely-numpy","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fxl0%2Flovely-numpy","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fxl0%2Flovely-numpy/lists"}