diff --git a/docs/source/contributing.rst b/docs/source/contributing.rst index 5b8b8f0e4..265d38637 100644 --- a/docs/source/contributing.rst +++ b/docs/source/contributing.rst @@ -32,10 +32,10 @@ To install ``mirdata`` for development purposes: .. code-block:: console pip install . - pip install .[tests] - pip install .[docs] - pip install .[dali] - pip install .[haydn_op20] + pip install ."[tests]" + pip install ."[docs]" + pip install ."[dali]" + pip install ."[haydn_op20]" We recommend to install `pyenv `_ to manage your Python versions @@ -62,7 +62,7 @@ Finally, run: .. code-block:: bash - pytest -vv --cov-report term-missing --cov-report=xml --cov=mirdata --black tests/ --local + pytest -vv --cov-report term-missing --cov-report=xml --cov=mirdata tests/ --local All tests should pass! @@ -98,7 +98,7 @@ dataset which is necessary for the loading and validating functionalities of ``m information about the files included in the dataset, their location and checksums. The necessary steps are: 1. To create an index, first create a script in ``scripts/``, as ``make_dataset_index.py``, which generates an index file. -2. Then run the script on the the dataset and save the index in ``mirdata/datasets/indexes/`` as ``dataset_index_.json``. +2. Then run the script on the dataset and save the index in ``mirdata/datasets/indexes/`` as ``dataset_index_.json``. where indicates which version of the dataset was used (e.g. 1.0). @@ -118,8 +118,8 @@ tracks ^^^^^^ Most MIR datasets are organized as a collection of tracks and annotations. In such case, the index should make use of the ``tracks`` -top-level key. A dictionary should be stored under the ``tracks`` top-level key where the keys are the unique track ids of the dataset. -The values are a dictionary of files associated with a track id, along with their checksums. These files can be for instance audio files +top-level key. A dictionary should be stored under the ``tracks`` top-level key where the keys are the unique track ids of the dataset. +The values are a dictionary of files associated with a track id, along with their checksums. These files can be for instance audio files or annotations related to the track id. File paths are relative to the top level directory of a dataset. .. admonition:: Index Examples - Tracks @@ -198,7 +198,7 @@ multitracks .. admonition:: Index Examples - Multitracks :class: dropdown - + If the version `1.0` of a given multitrack dataset has the structure: .. code-block:: javascript @@ -223,15 +223,15 @@ multitracks The top level directory is ``Example_Dataset`` and the relative path for ``multitrack1-voice1`` would be ``audio/multitrack1-voice1.wav``. Any unavailable fields are indicated with `null`. A possible index file for this example would be: - + .. code-block:: javascript - { + { "version": 1, "tracks": { "multitrack1-voice": { - "audio_voice1": ('audio/multitrack1-voice1.wav', checksum), - "audio_voice2": ('audio/multitrack1-voice1.wav', checksum), + "audio_voice1": ('audio/multitrack1-voice1.wav', checksum), + "audio_voice2": ('audio/multitrack1-voice1.wav', checksum), "voice-f0": ('annotations/multitrack1-voice-f0.csv', checksum) } "multitrack1-accompaniment": { @@ -242,7 +242,7 @@ multitracks }, "multitracks": { "multitrack1": { - "tracks": ['multitrack1-voice', 'multitrack1-accompaniment'], + "tracks": ['multitrack1-voice', 'multitrack1-accompaniment'], "audio": ('audio/multitrack1-mix.wav', checksum) "f0": ('annotations/multitrack1-f0.csv', checksum) } @@ -255,8 +255,8 @@ multitracks ] } } - - Note that in this examples we group ``audio_voice1`` and ``audio_voice2`` in a single Track because the annotation ``voice-f0`` annotation corresponds to their mixture. In contrast, the annotation ``voice-f0`` is extracted from the multitrack mix and it is stored in the ``multitracks`` group. The multitrack ``multitrack1`` has an additional track ``multitrack1-mix.wav`` which may be the master track, the final mix, the recording of ``multitrack1`` with another microphone. + + Note that in this examples we group ``audio_voice1`` and ``audio_voice2`` in a single Track because the annotation ``voice-f0`` annotation corresponds to their mixture. In contrast, the annotation ``voice-f0`` is extracted from the multitrack mix and it is stored in the ``multitracks`` group. The multitrack ``multitrack1`` has an additional track ``multitrack1-mix.wav`` which may be the master track, the final mix, the recording of ``multitrack1`` with another microphone. records @@ -279,7 +279,7 @@ To quickstart a new module: 1. Copy the example below and save it to ``mirdata/datasets/.py`` 2. Find & Replace ``Example`` with the . -3. Remove any lines beginning with `# --` which are there as guidelines. +3. Remove any lines beginning with `# --` which are there as guidelines. .. admonition:: Example Module :class: dropdown @@ -316,16 +316,16 @@ To finish your contribution, include tests that check the integrity of your load * For each audio/annotation file, reduce the audio length to 1-2 seconds and remove all but a few of the annotations. * If the dataset has a metadata file, reduce the length to a few lines. -2. Test all of the dataset specific code, e.g. the public attributes of the Track class, the load functions and any other +2. Test all of the dataset specific code, e.g. the public attributes of the Track class, the load functions and any other custom functions you wrote. See the `tests folder `_ for reference. - If your loader has a custom download function, add tests similar to + If your loader has a custom download function, add tests similar to `this loader `_. -3. Locally run ``pytest -s tests/test_full_dataset.py --local --dataset my_dataset`` before submitting your loader to make +3. Locally run ``pytest -s tests/test_full_dataset.py --local --dataset my_dataset`` before submitting your loader to make sure everything is working. If your dataset has `multiple versions `_, test each (non-default) version by running ``pytest -s tests/test_full_dataset.py --local --dataset my_dataset --dataset-version my_version``. -.. note:: We have written automated tests for all loader's ``cite``, ``download``, ``validate``, ``load``, ``track_ids`` functions, +.. note:: We have written automated tests for all loader's ``cite``, ``download``, ``validate``, ``load``, ``track_ids`` functions, as well as some basic edge cases of the ``Track`` class, so you don't need to write tests for these! @@ -379,10 +379,10 @@ Finally, there is one local test you should run, which we can't easily run in ou pytest -s tests/test_full_dataset.py --local --dataset dataset -Where ``dataset`` is the name of the module of the dataset you added. The ``-s`` tells pytest not to skip print -statments, which is useful here for seeing the download progress bar when testing the download function. +Where ``dataset`` is the name of the module of the dataset you added. The ``-s`` tells pytest not to skip print +statements, which is useful here for seeing the download progress bar when testing the download function. -This tests that your dataset downloads, validates, and loads properly for every track. This test takes a long time +This tests that your dataset downloads, validates, and loads properly for every track. This test takes a long time for some datasets, but it's important to ensure the integrity of the library. The ``--skip-download`` flag can be added to ``pytest`` command to run the tests skipping the download. @@ -446,9 +446,9 @@ it will simplify the reviewing process and also help you make a complete PR. You Docs ^^^^ -Staged docs for every new PR are built, and you can look at them by clicking on the "readthedocs" test in a PR. -To quickly troubleshoot any issues, you can build the docs locally by nagivating to the ``docs`` folder, and running -``make html`` (note, you must have ``sphinx`` installed). Then open the generated ``_build/source/index.html`` +Staged docs for every new PR are built, and you can look at them by clicking on the "readthedocs" test in a PR. +To quickly troubleshoot any issues, you can build the docs locally by navigating to the ``docs`` folder, and running +``make html`` (note, you must have ``sphinx`` installed). Then open the generated ``_build/source/index.html`` file in your web browser to view. Troubleshooting @@ -479,10 +479,10 @@ If github shows a red ``X`` next to your latest commit, it means one of our chec 4. the test coverage is too low -- this means that there are too many new lines of code introduced that are not tested. -5. the docs build has failed -- this means that one of the changes you made to the documentation has caused the build to fail. +5. the docs build has failed -- this means that one of the changes you made to the documentation has caused the build to fail. Check the formatting in your changes and make sure they are consistent. -6. the tests have failed -- this means at least one of the tests is failing. Run the tests locally to make sure they are passing. +6. the tests have failed -- this means at least one of the tests is failing. Run the tests locally to make sure they are passing. If they are passing locally but failing in the check, open an `issue` and we can help debug. @@ -501,7 +501,7 @@ cases, we aim to make sure that the version used in mirdata is the original one, **Before starting** a PR, if a dataset **is not fully downloadable**: 1. Contact the mirdata team by opening an issue or PR so we can discuss how to proceed with the closed dataset. -2. Show that the version used to create the checksum is the "canonical" one, either by getting the version from the +2. Show that the version used to create the checksum is the "canonical" one, either by getting the version from the dataset creator, or by verifying equivalence with several other copies of the dataset. @@ -511,18 +511,18 @@ Datasets needing extra dependencies ----------------------------------- If a new dataset requires a library that is not included setup.py, please open an issue. -In general, if the new library will be useful for many future datasets, we will add it as a +In general, if the new library will be useful for many future datasets, we will add it as a dependency. If it is specific to one dataset, we will add it as an optional dependency. To add an optional dependency, add the dataset name as a key in `extras_require` in setup.py, -and list any additional dependencies. Additionally, mock the dependecies in docs/conf.py +and list any additional dependencies. Additionally, mock the dependencies in docs/conf.py by adding it to the `autodoc_mock_imports` list. When importing these optional dependencies in the dataset module, use a try/except clause and log instructions if the user hasn't installed the extra -requriements. +requirements. -For example, if a module called `example_dataset` requires a module called `asdf`, +For example, if a module called `example_dataset` requires a module called `asdf`, it should be imported as follows: .. code-block:: python @@ -546,7 +546,7 @@ There are some datasets where the loading code is the same, but there are multip versions of the data (e.g. updated annotations, or an additional set of tracks which follow the same paradigm). In this case, only one loader should be written, and multiple versions can be defined by creating additional indexes. Indexes follow the -naming convention _index_.json, thus a dataset with two +naming convention _index_.json, thus a dataset with two versions simply has two index files. Different versions are tracked using the ``INDEXES`` variable: @@ -565,7 +565,7 @@ By default, mirdata loads the version specified as ``default`` in ``INDEXES`` when running ``mirdata.initialize('example')``, but a specific version can be loaded by running ``mirdata.initialize('example', version='2.0')``. -Different indexes can refer to different subsets of the same larger dataset, +Different indexes can refer to different subsets of the same larger dataset, or can reference completely different data. All data needed for all versions should be specified via keys in ``REMOTES``, and by default, mirdata will download everything. If one version only needs a subset @@ -593,7 +593,7 @@ Large indexes should be stored remotely, rather than checked in to the mirdata r mirdata has a `zenodo community `_ where larger indexes can be uploaded as "datasets". -When defining a remote index in ``INDEXES``, simply also pass the arguments ``url`` and +When defining a remote index in ``INDEXES``, simply also pass the arguments ``url`` and ``checksum`` to the ``Index`` class: .. code-block:: python @@ -624,7 +624,7 @@ Here are some common examples. .. note:: The small formatting details in these examples are important. Differences in new lines, indentation, and spacing make a difference in how the documentation is rendered. For example writing ``Returns:`` will render correctly, but ``Returns`` - or ``Returns :`` will not. + or ``Returns :`` will not. Functions: @@ -736,10 +736,10 @@ it with a try/except: file_path = "flululu.txt" if not os.path.exists(file_path): raise FileNotFoundError(f"{file_path} not found, did you run .download?") - + with open(file_path, "r") as fhandle: ... - + # replacement code that is compatible with remote filesystems try: with open(file_path, "r") as fhandle: diff --git a/docs/source/overview.rst b/docs/source/overview.rst index 0e3949229..7b8122d79 100644 --- a/docs/source/overview.rst +++ b/docs/source/overview.rst @@ -9,9 +9,9 @@ Overview pip install mirdata -``mirdata`` is a library which aims to standardize how audio datasets are accessed in Python, +``mirdata`` is a library which aims to standardize how audio datasets are accessed in Python, removing the need for writing custom loaders in every project, and improving reproducibility. -Working with datasets usually requires an often cumbersome step of downloading data and writing +Working with datasets usually requires an often cumbersome step of downloading data and writing load functions that load related files (for example, audio and annotations) into a standard format to be used for experimenting or evaluating. ``mirdata`` does all of this for you: @@ -49,9 +49,9 @@ mirdata design principles Ease of use and contribution ---------------------------- -We designed ``mirdata`` to be easy to use and easy to contribute to. ``mirdata`` simplifies the research pipeline considerably, -facilitating research in a wider diversity of tasks and musical datasets. We provide detailed examples on how to interact with -the library in the :ref:`tutorial`, as well as detail explanation on how to contribute in :ref:`contributing`. Additionally, +We designed ``mirdata`` to be easy to use and easy to contribute to. ``mirdata`` simplifies the research pipeline considerably, +facilitating research in a wider diversity of tasks and musical datasets. We provide detailed examples on how to interact with +the library in the :ref:`tutorial`, as well as detail explanation on how to contribute in :ref:`contributing`. Additionally, we have a `repository of Jupyter notebooks `_ with usage examples of the different datasets. @@ -59,27 +59,27 @@ examples of the different datasets. Reproducibility --------------- -We aim for ``mirdata`` to aid in increasing research reproducibility by providing a common framework for MIR researchers to -compare and validate their data. If mistakes are found in annotations or audio versions change, using ``mirdata``, the community +We aim for ``mirdata`` to aid in increasing research reproducibility by providing a common framework for MIR researchers to +compare and validate their data. If mistakes are found in annotations or audio versions change, using ``mirdata``, the community can fix mistakes while still being able to compare methods moving forward. .. _canonical version: canonical versions ^^^^^^^^^^^^^^^^^^ -The ``dataset loaders`` in ``mirdata`` are written for what we call the ``canonical version`` of a dataset. Whenever possible, -this should be the official release of the dataset as published by the dataset creator/s. When this is not possible, (e.g. for -data that is no longer available), the procedure we follow is to find as many copies of the data as possible from different researchers -(at least 4), and use the most common one. To make this process transparent, when there are doubts about the data consistency we open an +The ``dataset loaders`` in ``mirdata`` are written for what we call the ``canonical version`` of a dataset. Whenever possible, +this should be the official release of the dataset as published by the dataset creator/s. When this is not possible, (e.g. for +data that is no longer available), the procedure we follow is to find as many copies of the data as possible from different researchers +(at least 4), and use the most common one. To make this process transparent, when there are doubts about the data consistency we open an `issue `_ and leave it to the community to discuss what to use. Standardization --------------- -Different datasets have different annotations, metadata, etc. We try to respect the idiosyncracies of each dataset as much as we can. For this +Different datasets have different annotations, metadata, etc. We try to respect the idiosyncrasies of each dataset as much as we can. For this reason, ``tracks`` in each ``Dataset`` in ``mirdata`` have different attributes, e.g. some may have ``artist`` information and some may not. -However there are some elements that are common in most datasets, and in these cases we standarize them to increase the usability of the library. +However there are some elements that are common in most datasets, and in these cases we standardize them to increase the usability of the library. Some examples of this are the annotations in ``mirdata``, e.g. ``BeatData``. @@ -130,10 +130,10 @@ top-level keys ``metadata``, ``tracks``, ``multitracks`` or ``records``. An inde The optional top-level keys (`tracks`, `multitracks` and `records`) relate to different organizations of music datasets. -`tracks` are used when a dataset is organized as a collection of individual tracks, namely mono or multi-channel audio, +`tracks` are used when a dataset is organized as a collection of individual tracks, namely mono or multi-channel audio, spectrograms only, and their respective annotations. `multitracks` are used in when a dataset comprises of -multitracks - different groups of tracks which are directly related to each other. Finally, `records` are used when a dataset -consits of groups of tables (e.g. relational databases), as many recommendation datasets do. +multitracks - different groups of tracks which are directly related to each other. Finally, `records` are used when a dataset +consists of groups of tables (e.g. relational databases), as many recommendation datasets do. See the contributing docs :ref:`create_index` for more information about mirdata indexes. @@ -142,7 +142,7 @@ See the contributing docs :ref:`create_index` for more information about mirdata annotations ########### -mirdata provdes ``Annotation`` classes of various kinds which provide a standard interface to different +mirdata provides ``Annotation`` classes of various kinds which provide a standard interface to different annotation formats. These classes are compatible with the ``mir_eval`` library's expected format, as well as with the jams format. The format can be easily extended to other formats, if requested. @@ -150,5 +150,5 @@ as with the jams format. The format can be easily extended to other formats, if metadata ######## -When available, we provide extensive and easy-to-access ``metadata`` to facilitate track metadata-specific analysis. -``metadata`` is available as attroibutes at the ``track`` level, e.g. ``track.artist``. +When available, we provide extensive and easy-to-access ``metadata`` to facilitate track metadata-specific analysis. +``metadata`` is available as attributes at the ``track`` level, e.g. ``track.artist``. diff --git a/docs/source/quick_reference.rst b/docs/source/quick_reference.rst index 88de872db..0b3bbc6f5 100644 --- a/docs/source/quick_reference.rst +++ b/docs/source/quick_reference.rst @@ -75,8 +75,8 @@ one another, as multiple drums can be played at the same time. F0 ^^ -Musical pitch contours, typically encoded as time series indidcating the musical pitch over time. -The time series typically have evenly spaced timestamps, each with a correspoinding pitch value +Musical pitch contours, typically encoded as time series indicating the musical pitch over time. +The time series typically have evenly spaced timestamps, each with a corresponding pitch value which may be encoded in a number of formats/granularities, including midi note numbers and Hertz. .. _genre: @@ -128,7 +128,7 @@ many subdivisions and the length of this subdivisions that we do have per each m Melody ^^^^^^ The musical melody of a song. Melody has no universal definition and is typically defined per dataset. -It is typically enocoded as F0_ or as Notes_. Other types of annotations such as Vocal F0 or Vocal Notes +It is typically encoded as F0_ or as Notes_. Other types of annotations such as Vocal F0 or Vocal Notes can often be considered as melody annotations as well. .. _notes: @@ -166,7 +166,7 @@ include labels for sections, which may indicate repetitions and/or the section t Segments ^^^^^^^^ -Segments of particular musical events, e.g. segments of note stability, segments of particular melodic +Segments of particular musical events, e.g. segments of note stability, segments of particular melodic event, and many more. .. _technique: @@ -224,4 +224,4 @@ The absolute tonic of a track. It may refer to the tonic a single stroke, or the a track. -.. _article: https://link.springer.com/article/10.1007/s10844-013-0250-y \ No newline at end of file +.. _article: https://link.springer.com/article/10.1007/s10844-013-0250-y diff --git a/docs/source/tutorial.rst b/docs/source/tutorial.rst index 41dd50e3b..9743bad3a 100644 --- a/docs/source/tutorial.rst +++ b/docs/source/tutorial.rst @@ -125,7 +125,7 @@ A partial download example for ``cante100`` dataset could be: Validating a dataset ^^^^^^^^^^^^^^^^^^^^ -Using the method ``validate()`` we can check if the files in the local version are the same than the available canical version, +Using the method ``validate()`` we can check if the files in the local version are the same than the available canonical version, and the files were downloaded correctly (none of them are corrupted). For big datasets: In future ``mirdata`` versions, a random validation will be included. This improvement will reduce validation time for very big datasets. @@ -164,8 +164,8 @@ We can choose a random track from a dataset with the ``choice_track()`` method. ) -We can also access specific tracks by id. -The available track ids can be acessed via the ``.track_ids`` attribute. +We can also access specific tracks by id. +The available track ids can be accessed via the ``.track_ids`` attribute. In the next example we take the first track id, and then we retrieve the melody annotation. @@ -188,7 +188,7 @@ Alternatively, we don't need to load the whole dataset to get a single track. example_melody = example_track.melody # Get the melody from first track -.. _Remote Data Example: +.. _Remote Data Example: Accessing data on non-local filesystems ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -231,7 +231,7 @@ when initializing a dataset. For example: Annotation classes ^^^^^^^^^^^^^^^^^^ -``mirdata`` defines annotation-specific data classes. These data classes are meant to standarize the format for +``mirdata`` defines annotation-specific data classes. These data classes are meant to standardize the format for all loaders, and are compatibly with `jams `_ and `mir_eval `_. The list and descriptions of available annotation classes can be found in :ref:`annotations`. @@ -242,7 +242,7 @@ Iterating over datasets and annotations ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ In general, most datasets are a collection of tracks, and in most cases each track has an audio file along with annotations. -With the ``load_tracks()`` method, all tracks are loaded as a dictionary with the ids as keys and +With the ``load_tracks()`` method, all tracks are loaded as a dictionary with the ids as keys and track objects (which include their respective audio and annotations, which are lazy-loaded on access) as values. .. code-block:: python @@ -359,7 +359,7 @@ The following is a simple example of a generator that can be used to create a te import mirdata import numpy as np - import tensorflow as tf + import tensorflow as tf def orchset_generator(): # using the default data_home