.. _sec_imgdataset: Image Prediction - Properly load any image dataset as ImageDataset ================================================================== Preparing the dataset for ImagePredictor is not difficult at all, however, we'd like to introduce the recommended ways to initialize the dataset, so you will have smoother experience using ``autogluon.vision.ImagePredictor``. There are generally three ways to load a dataset for ImagePredictor: - Load a csv file or construct your own pandas ``DataFrame`` with ``image`` and ``label`` columns - Load a image folder directly with ``ImageDataset`` - Convert a list of images to dataset directly with ``ImageDataset`` We will go through these four methods one by one. First of all, let's import autogluon .. code:: python %matplotlib inline import autogluon.core as ag from autogluon.vision import ImageDataset import pandas as pd .. parsed-literal:: :class: output /var/lib/jenkins/workspace/workspace/autogluon-tutorial-image-classification-v3/venv/lib/python3.7/site-packages/gluoncv/__init__.py:40: UserWarning: Both `mxnet==1.7.0` and `torch==1.7.1+cu101` are installed. You might encounter increased GPU memory footprint if both framework are used at the same time. warnings.warn(f'Both `mxnet=={mx.__version__}` and `torch=={torch.__version__}` are installed. ' Load a csv file or construct a DataFrame object ----------------------------------------------- We use a csv file from PetFinder competition as an example. You may use any tabular data as long as you can create ``image``\ (absolute or relative paths to images) and ``label``\ (category for each image) columns. .. code:: python csv_file = ag.utils.download('https://autogluon.s3-us-west-2.amazonaws.com/datasets/petfinder_example.csv') df = pd.read_csv(csv_file) df.head() .. parsed-literal:: :class: output 100%|██████████| 820/820 [00:00<00:00, 38761.74KB/s] .. raw:: html
image PetID label
0 petfinder_data/train_images/015da9e87-1.jpg 015da9e87 0
1 petfinder_data/train_images/022606901-1.jpg 022606901 0
2 petfinder_data/train_images/02f89bdcb-1.jpg 02f89bdcb 0
3 petfinder_data/train_images/03f217352-1.jpg 03f217352 0
4 petfinder_data/train_images/040a9a6f9-1.jpg 040a9a6f9 0
If the image paths are not relative to current working directory, you may use the helper function to prepend prefix for each image, using absolute paths can reduce the chance of OSError happening to file access: .. code:: python df = ImageDataset.from_csv(csv_file, root='/home/ubuntu') df.head() .. raw:: html
image PetID label
0 /home/ubuntu/petfinder_data/train_images/015da... 015da9e87 0
1 /home/ubuntu/petfinder_data/train_images/02260... 022606901 0
2 /home/ubuntu/petfinder_data/train_images/02f89... 02f89bdcb 0
3 /home/ubuntu/petfinder_data/train_images/03f21... 03f217352 0
4 /home/ubuntu/petfinder_data/train_images/040a9... 040a9a6f9 0
Or you can perform the correction by yourself: .. code:: python import os df['image'] = df['image'].apply(lambda x: os.path.join('/home/ubuntu', x)) df.head() .. raw:: html
image PetID label
0 /home/ubuntu/petfinder_data/train_images/015da... 015da9e87 0
1 /home/ubuntu/petfinder_data/train_images/02260... 022606901 0
2 /home/ubuntu/petfinder_data/train_images/02f89... 02f89bdcb 0
3 /home/ubuntu/petfinder_data/train_images/03f21... 03f217352 0
4 /home/ubuntu/petfinder_data/train_images/040a9... 040a9a6f9 0
Otherwise you may use the ``DataFrame`` as-is, ``ImagePredictor`` will apply auto conversion during ``fit`` to ensure other metadata is available for training. You can have multiple columns in the ``DataFrame``, ``ImagePredictor`` only cares about ``image`` and ``label`` columns during training. Load an image directory ----------------------- It's pretty common that sometimes you only have a folder of images, organized by the category names. Recursively loop through images is tedious. You can use ``ImageDataset.from_folders`` or ``ImageDataset.from_folder`` to avoid implementing recursive search. The difference between ``from_folders`` and ``from_folder`` is the targeting folder structure. If you have a folder with splits, e.g., ``train``, ``test``, like: - root/train/car/0001.jpg - root/train/car/xxxa.jpg - root/val/bus/123.png - root/test/bus/023.jpg Then you can load the splits with ``from_folders``: .. code:: python train_data, _, test_data = ImageDataset.from_folders('https://autogluon.s3.amazonaws.com/datasets/shopee-iet.zip', train='train', test='test') print('train #', len(train_data), 'test #', len(test_data)) train_data.head() .. parsed-literal:: :class: output data/ ├── test/ └── train/ train # 800 test # 80 .. raw:: html
image label
0 /var/lib/jenkins/.gluoncv/datasets/shopee-iet/... 0
1 /var/lib/jenkins/.gluoncv/datasets/shopee-iet/... 0
2 /var/lib/jenkins/.gluoncv/datasets/shopee-iet/... 0
3 /var/lib/jenkins/.gluoncv/datasets/shopee-iet/... 0
4 /var/lib/jenkins/.gluoncv/datasets/shopee-iet/... 0
If you have a folder without ``train`` or ``test`` root folders, like: - root/car/0001.jpg - root/car/xxxa.jpg - root/bus/123.png - root/bus/023.jpg Then you can load the splits with ``from_folder``: .. code:: python # use the train from shopee-iet as new root root = os.path.join(os.path.dirname(train_data.iloc[0]['image']), '..') all_data = ImageDataset.from_folder(root) all_data.head() .. raw:: html
image label
0 /var/lib/jenkins/.gluoncv/datasets/shopee-iet/... 0
1 /var/lib/jenkins/.gluoncv/datasets/shopee-iet/... 0
2 /var/lib/jenkins/.gluoncv/datasets/shopee-iet/... 0
3 /var/lib/jenkins/.gluoncv/datasets/shopee-iet/... 0
4 /var/lib/jenkins/.gluoncv/datasets/shopee-iet/... 0
.. code:: python # you can manually split the dataset or use `random_split` train, val, test = all_data.random_split(val_size=0.1, test_size=0.1) print('train #:', len(train), 'test #:', len(test)) .. parsed-literal:: :class: output train #: 646 test #: 83 Convert a list of images to dataset ----------------------------------- You can create dataset from a list of images with a function, the function is used to determine the label of each image. We use the Oxford-IIIT Pet Dataset mini pack as an example, where images are scattered in ``images`` directory but with unique pattern: filenames of cat starts with capital letter, otherwise dogs. So we can use a function to distinguish and assign label to each image: .. code:: python pets = ag.utils.download('https://autogluon.s3-us-west-2.amazonaws.com/datasets/oxford-iiit-pet-mini.zip') pets = ag.utils.unzip(pets) image_list = [x for x in os.listdir(os.path.join(pets, 'images')) if x.endswith('jpg')] def label_fn(x): return 'cat' if os.path.basename(x)[0].isupper() else 'dog' new_data = ImageDataset.from_name_func(image_list, label_fn, root=os.path.join(os.getcwd(), pets, 'images')) new_data .. parsed-literal:: :class: output 100%|██████████| 35730/35730 [00:01<00:00, 23404.71KB/s] .. raw:: html
image label
0 /var/lib/jenkins/workspace/workspace/autogluon... 0
1 /var/lib/jenkins/workspace/workspace/autogluon... 0
2 /var/lib/jenkins/workspace/workspace/autogluon... 0
3 /var/lib/jenkins/workspace/workspace/autogluon... 1
4 /var/lib/jenkins/workspace/workspace/autogluon... 0
... ... ...
95 /var/lib/jenkins/workspace/workspace/autogluon... 0
96 /var/lib/jenkins/workspace/workspace/autogluon... 1
97 /var/lib/jenkins/workspace/workspace/autogluon... 1
98 /var/lib/jenkins/workspace/workspace/autogluon... 1
99 /var/lib/jenkins/workspace/workspace/autogluon... 1

100 rows × 2 columns

Visualize images ---------------- You can use ``show_images`` to visualize the images, as well as the corresponding labels: .. code:: python new_data.show_images() .. figure:: output_dataset_4aa41c_16_0.png For raw DataFrame objects, you can convert them to Dataset first to use ``show_images``. Congratulations, you can now proceed to :ref:`sec_imgquick` to start training the ``ImagePredictor``.