Takes a list and return a dict of distinct values pointing to a list of index locations of each value I came up with a way to get a dict of distinct elements in a list pointing to the location of each element; it works, but I feel pretty awful about this code, it's very ugly. Is there a more natural/pythonic way to do this?
from itertools import groupby
sample_data = [1,2,3,3,1,0,5]
give_groups = lambda dta: {item: list(map(lambda z: z[0], list(item_group))) for item, item_group in itertools.groupby(list(enumerate(dta)), lambda x:x[1])}
print(give_groups(sample_data))

{1: [4], 2: [1], 3: [2, 3], 0: [5], 5: [6]}

The performance is also bad.
Created this alternate that does work, but is kinda slow:
def alt_grouping(dta):
    retdict = defaultdict(list)
    for position, item in enumerate(dta):
        retdict[item].append(position)
    return retdict
The first try :
from itertools import groupby
sample_data = [1,2,3,3,1,0,5]
give_groups = lambda dta: {item: list(map(lambda z: z[0], list(item_group))) for item, item_group in itertools.groupby(list(enumerate(dta)), lambda x:x[1])}
print(give_groups(sample_data))

Have to be corrected to:
from itertools import groupby # --&gt; you don't have to call itertools.groupby just groupby
sample_data = [1,2,3,3,1,0,5]
give_groups = lambda dta: {item: list(map(lambda z: z[0], list(item_group))) for item, item_group in groupby(list(enumerate(dta)), lambda x:x[1])}
print(give_groups(sample_data))

But seems to be replacing items and not appending them, don't see why.

In the alt_grouping function, defaultdict doesn't exists:
def alt_grouping(dta):
    retdict = defaultdict(list) # don't know what is defaultdict
    for position, item in enumerate(dta):
        retdict[item].append(position)
    return retdict

Then I found a solution that works, it's based on your function alt_grouping:
sample_data = [1,2,3,3,1,0,5]

retdict = {}
for position, item in enumerate(sample_data):
        if item in retdict.keys():
            retdict[item].append(position)
        else:
            retdict[item] = [position]

print(retdict)

I take some execution &amp; times testing in the first try and my alternative with a bigger sample a list of two range(100).
Sample Data:
 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 
77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99]

First Function:
{0: [100], 1: [101], 2: [102], 3: [103], 4: [104], 5: [105], 6: [106], 7: [107], 8: [108], 9: [109], 10: [110], 11: [111], 12: [112], 13: [113], 14: [114], 15: [115], 16: [116], 17: [117], 18: [118], 19: [119], 20: [120], 21: [121], 22: [122], 23: [123], 24: [124], 25: [125], 26: [126], 27: [127], 28: [128], 29: [129], 30: [130], 31: [131], 32: [132], 33: [133], 34: [134], 35: [135], 36: [136], 37: [137], 38: [138], 39: [139], 40: [140], 41: [141], 42: [142], 43: [143], 44: [144], 45: [145], 46: [146], 47: [147], 48: [148], 49: [149], 50: [150], 51: [151], 52: [152], 53: [153], 54: [154], 55: [155], 56: [156], 57: [157], 58: [158], 59: [159], 60: [160], 61: [161], 62: [162], 63: [163], 64: [164], 65: [165], 66: [166], 67: [167], 68: [168], 69: [169], 70: [170], 71: [171], 72: [172], 73: [173], 74: [174], 75: [175], 76: [176], 77: [177], 78: [178], 79: [179], 80: [180], 81: [181], 82: [182], 83: [183], 84: [184], 85: [185], 86: [186], 87: [187], 88: [188], 89: [189], 90: [190], 91: [191], 92: [192], 93: [193], 94: [194], 95: [195], 96: [196], 97: [197], 98: [198], 99: [199]}
--- 0.001995563507080078 seconds ---
My Function:
{0: [0, 100], 1: [1, 101], 2: [2, 102], 3: [3, 103], 4: [4, 104], 5: [5, 105], 6: [6, 106], 7: [7, 107], 8: [8, 108], 9: [9, 109], 10: [10, 110], 11: [11, 111], 12: [12, 112], 13: [13, 113], 14: [14, 114], 15: [15, 115], 16: [16, 
116], 17: [17, 117], 18: [18, 118], 19: [19, 119], 20: [20, 120], 21: [21, 121], 22: [22, 122], 23: [23, 123], 24: [24, 124], 25: [25, 125], 26: [26, 126], 27: [27, 127], 28: [28, 128], 29: [29, 129], 30: [30, 130], 31: [31, 131], 32: [32, 132], 33: [33, 133], 34: [34, 134], 35: [35, 135], 36: [36, 136], 37: [37, 137], 38: [38, 138], 39: [39, 139], 40: [40, 140], 41: [41, 141], 42: [42, 142], 43: [43, 143], 44: [44, 144], 45: [45, 145], 46: [46, 146], 47: 
[47, 147], 48: [48, 148], 49: [49, 149], 50: [50, 150], 51: [51, 151], 52: [52, 152], 53: [53, 153], 54: [54, 154], 55: [55, 155], 56: [56, 156], 57: [57, 157], 58: [58, 158], 59: [59, 159], 60: [60, 160], 61: [61, 161], 62: [62, 
162], 63: [63, 163], 64: [64, 164], 65: [65, 165], 66: [66, 166], 67: [67, 167], 68: [68, 168], 69: [69, 169], 70: [70, 170], 71: [71, 171], 72: [72, 172], 73: [73, 173], 74: [74, 174], 75: [75, 175], 76: [76, 176], 77: [77, 177], 78: [78, 178], 79: [79, 179], 80: [80, 180], 81: [81, 181], 82: [82, 182], 83: [83, 183], 84: [84, 184], 85: [85, 185], 86: [86, 186], 87: [87, 187], 88: [88, 188], 89: [89, 189], 90: [90, 190], 91: [91, 191], 92: [92, 192], 93: 
[93, 193], 94: [94, 194], 95: [95, 195], 96: [96, 196], 97: [97, 197], 98: [98, 198], 99: [99, 199]}
--- 0.0009963512420654297 seconds ---

Seems to be pretty similar then I try with list(range(10000)):
First Function:
--- 0.015984535217285156 seconds ---
My Function:
--- 0.005953311920166016 seconds ---

Here we see a difference.
There is the code for tests - EDITED :
import time
sample_data = list(range(1000000)) + list (range(1000000))
# print (&quot;Sample Data:\n&quot;,sample_data, &quot;\n&quot;)

print(&quot;First Function:&quot;)
start_time = time.time()

from itertools import groupby
give_groups = lambda dta: {item: list(map(lambda z: z[0], list(item_group))) for item, item_group in groupby(list(enumerate(dta)), lambda x:x[1])}
# print(give_groups(sample_data))
give_groups(sample_data)

print(&quot;--- %s seconds ---&quot; % (time.time() - start_time))


print(&quot;My Function:&quot;)
start_time = time.time()
retdict = {}
for position, item in enumerate(sample_data):
        if item in retdict.keys():
            retdict[item].append(position)
        else:
            retdict[item] = [position]

print(&quot;--- %s seconds ---&quot; % (time.time() - start_time))



print(&quot;Other Function:&quot;)

from collections import defaultdict

start_time = time.time()
def dict_with_indices(dta):
    &quot;&quot;&quot; Returns a dictionary with a list of indices for each item in dta

    Args:
        dta (list): list of data to be indexed

    Returns:
        dict: dict with list of indices as values

    Examples:
        &gt;&gt;&gt; dict_with_indices([1,2,3,3,1,0,5]]
        {1: [0, 4], 2: [1], 3: [2, 3], 0: [5], 5: [6]}
    &quot;&quot;&quot;
    result = defaultdict(list)
    for idx, val in enumerate(dta):
        result[val].append(idx)
    return result

dict_with_indices(sample_data)

print(&quot;--- %s seconds ---&quot; % (time.time() - start_time))

Times for this new tests:
First Function:
--- 1.9537413120269775 seconds ---
My Function:
--- 0.7061352729797363 seconds ---
Other Function:
--- 0.6053769588470459 seconds ---

New Solution seems to be the better one, thanks to @agtoever :
from collections import defaultdict
    

    def dict_with_indices(dta):
        &quot;&quot;&quot; Returns a dictionary with a list of indices for each item in dta
    
        Args:
            dta (list): list of data to be indexed
    
        Returns:
            dict: dict with list of indices as values
    
        Examples:
            &gt;&gt;&gt; dict_with_indices([1,2,3,3,1,0,5]]
            {1: [0, 4], 2: [1], 3: [2, 3], 0: [5], 5: [6]}
        &quot;&quot;&quot;
        result = defaultdict(list)
        for idx, val in enumerate(dta):
            result[val].append(idx)
        return result
    
    dict_with_indices(sample_data)