Home > database >  Special list view
Special list view

Time:11-03

Having a list like:

 >>> l = [0, 1, 1, 1, 0, 2, 2, 2, 0]

How could I implement a Proxy that computes the sum of the repeated numbers, and the indexing operation behaves like:

>>> proxy = Proxy(l) 
>>> proxy[0]
0
>>> proxy[1] 
3 
>>> proxy[2]  
0     
>>> proxy[3] 
6 
>>> proxy[4]  
0 

The underlying list must be invariant. The Proxy would be a class that receives the list and implements getitem, like:

class Proxy:
    
    def __init__(self, l):
        self.l = l 

    def __getitem__(self, index):
        pass 

I need some kind of "on the fly" computation in the getitem method. I need to keep the list absolutely invariant, in order to leverage some framework.

CodePudding user response:

You can use itertools.groupby and sum:

from itertools import groupby

proxy = lambda lst: [sum(g) for _, g in groupby(lst)]

p = proxy([0, 1, 1, 1, 0, 2, 2, 2, 0])
p
# [0, 3, 0, 6, 0]

Or as a class:

class Proxy:
    def __init__(self, l):
        self.l = l
        self._data = [sum(g) for _, g in groupby(iterable)]
    def __getitem__(self, index):
        return self._data[index]

Some docs:

CodePudding user response:

I didn't quite understand your question. But I've implemented a simple function to do as you wanted. (Or at least what I think you've wanted)

def Proxy(lst):
    result = [0]
    last_value = lst[0]
    for item in lst:
        if item == last_value:
            result[len(result)-1]  = item
        else:
            result.append(item)
        last_value = item
    return result

CodePudding user response:

I would simply iterate on the list, keeping the previous value to compare. Something like:

from typing import List
def proxy(lst: List[int]):
    res = {}
    prev = None  # Initial value, would be different from first item
    index = -1   # Initial value, would be incremented on first item
    for num in lst:
        if num == prev:
            res[index]  = num
        else:
            index  = 1
            res[index] = num
        prev = num
    return res

CodePudding user response:

from collections import Counter


class View:
    def __init__(self, l):
        self.l = Counter(l)

    def __getitem__(self, index):
        return self.l.get(index, 0) * index


proxy = View([0, 1, 1, 1, 0, 2, 2, 2, 0])
print(proxy[2]) #6
  • Related