def random_split(sample_collection, split_fracs, seed=None):
    """Generates a random partition of the samples in the collection according
    to the specified split fractions.

    Example::

        import fiftyone as fo
        import fiftyone.utils.random as four
        import fiftyone.zoo as foz

        # A dataset with `ground_truth` detections and no tags
        dataset = (
            foz.load_zoo_dataset("quickstart")
            .select_fields("ground_truth")
            .set_field("tags", [])
        ).clone()

        #
        # Generate a random sample and encode results via tags
        #

        four.random_split(dataset, {"train": 0.7, "test": 0.2, "val": 0.1})

        print(dataset.count_sample_tags())
        # {'train': 140, 'test': 40, 'val': 20}

        #
        # Generate a random sample in-memory
        #

        view1, view2 = four.random_split(dataset, [0.5, 0.5])

        assert len(view1) + len(view2) == len(dataset)
        assert set(view1.values("id")).isdisjoint(set(view2.values("id")))

    Args:
        sample_collection: a
            :class:`fiftyone.core.collections.SampleCollection`
        split_fracs: can be either of the following:

            -   a dict mapping tag strings to split fractions in ``[0, 1]``. In
                this case, the partition is denoted by tagging each sample with
                its assigned split
            -   a list of split fractions in ``[0, 1]``. In this case, a
                corresponding list of :class:`fiftyone.core.view.DatasetView`
                instances containing the partition is returned

            In either case, the split fractions are normalized so that they sum
            to 1, if necessary
        seed (None): an optional random seed

    Returns:
        one of the following

        -   ``None``, if ``split_fracs`` is a dict
        -   a tuple of :class:`fiftyone.core.view.DatasetView` instances, if
            ``split_fracs`` is a list
    """
    use_tags = isinstance(split_fracs, dict)

    if use_tags:
        tags, fracs = zip(*split_fracs.items())
    else:
        fracs = split_fracs

    fracs = np.cumsum(fracs)
    alpha = len(sample_collection) / fracs[-1]
    threshs = np.round(alpha * fracs).astype(int)

    sample_ids = np.array(sample_collection.values("id"))
    rs = np.random.RandomState(seed=seed)  # pylint: disable=no-member
    rs.shuffle(sample_ids)

    split_ids = np.split(sample_ids, threshs[:-1])

    if use_tags:
        for ids, tag in zip(split_ids, tags):
            sample_collection.select(ids).tag_samples(tag)

        return

    return tuple(sample_collection.select(ids) for ids in split_ids)
Generates a random partition of the samples in the collection according
    to the specified split fractions.

    Example::

        import fiftyone as fo
        import fiftyone.utils.random as four
        import fiftyone.zoo as foz

        # A dataset with `ground_truth` detections and no tags
        dataset = (
            foz.load_zoo_dataset("quickstart")
            .select_fields("ground_truth")
            .set_field("tags", [])
        ).clone()

        #
        # Generate a random sample and encode results via tags
        #

        four.random_split(dataset, {"train": 0.7, "test": 0.2, "val": 0.1})

        print(dataset.count_sample_tags())
        # {'train': 140, 'test': 40, 'val': 20}

        #
        # Generate a random sample in-memory
        #

        view1, view2 = four.random_split(dataset, [0.5, 0.5])

        assert len(view1) + len(view2) == len(dataset)
        assert set(view1.values("id")).isdisjoint(set(view2.values("id")))

    Args:
        sample_collection: a
            :class:`fiftyone.core.collections.SampleCollection`
        split_fracs: can be either of the following:

            -   a dict mapping tag strings to split fractions in ``[0, 1]``. In
                this case, the partition is denoted by tagging each sample with
                its assigned split
            -   a list of split fractions in ``[0, 1]``. In this case, a
                corresponding list of :class:`fiftyone.core.view.DatasetView`
                instances containing the partition is returned

            In either case, the split fractions are normalized so that they sum
            to 1, if necessary
        seed (None): an optional random seed

    Returns:
        one of the following

        -   ``None``, if ``split_fracs`` is a dict
        -   a tuple of :class:`fiftyone.core.view.DatasetView` instances, if
            ``split_fracs`` is a list
    
fiftyone/utils/random.py