Brex - Technical Phone Screen 2022 - Suspicious Activity
Anonymous User
1190

PLEASE UPVOTE IF THIS HELPS YOU!

Question:
We have a set of known suspicious user activities and a batch of new user activities. An activity is an ordered tuple of attributes. Using the known set, we want to find activities in the new batch that are suspicious.

To do so, we have set up a simple hypothesis -

An activity is suspicious if it is “similar” to any other suspicious activity, including suspicious activities from the new batch.
An activity is similar to another activity if they have the same values for at least k attributes.
Given the set of known suspicious activities, similarity factor k and the set of new activities, determine which of the new activities are suspicious according to the above hypothesis.

suspicious_activities = [
       ("Albert", "San Francisco", "deposit"),
       ("Brad", "San Francisco", "withdraw"),
       ("Claire", "New York", "withdraw")
]

new_activities = [
       ("Joe", "Miami", "withdraw"),
       ("John", "San Francisco", "deposit"),
       ("Diana", "London", "withdraw"),
       ("Diana", "San Francisco", "withdraw"),
       ("Albert", "London", "withdraw"),
       ("Joe", "New York", "update_address"),
       ("Claire", "Miami", "deposit"),
       ("Diana", "New York", "deposit"),
       ("Albert", "Chicago", "withdraw"),
       ("Brad", "Paris", "deposit"),
       ("Claire", "Paris", "deposit"),
       ("Diana", "Vancouver", "file_dispute"),
       ("John", "Mumbai", "withdraw")
]

# Number of equal attributes for "similarity", k = 2;

def find_suspicious_activities(suspicious_activities,new_activities,k=2):
    new_suspicious_activities = []
    
    cur_suspicious_activies = [0]
    
    visited = [False]*len(new_activities)
    
    while cur_suspicious_activies:
        cur_suspicious_activies.clear()
        for j,activity in enumerate(new_activities):
            if visited[j]:
                continue
            for suspicious_activity in suspicious_activities:
                if is_suspicious_activity(activity,suspicious_activity, k):
                    new_suspicious_activities.append(activity)
                    cur_suspicious_activies.append(activity)
                    visited[j] = True
                    break
        
        suspicious_activities.extend(cur_suspicious_activies)
    new_suspicious_activities.sort()
    
    return new_suspicious_activities
 
def is_suspicious_activity(activity, suspicious_activity, k):
    cur_k = 0
    for i in range(len(activity)):
        if suspicious_activity[i] == activity[i]:
            cur_k+=1
            if cur_k == k:
                return True
    return False
    
result = find_suspicious_activities(suspicious_activities, new_activities, k=2)

test_case = result == [
       ("Albert", "Chicago", "withdraw"),
       ("Albert", "London", "withdraw"),
       ("Diana", "London", "withdraw"),
       ("Diana", "San Francisco", "withdraw"),
       ("John", "San Francisco", "deposit"),
]
print(result)
print(test_case)
assert test_case
Comments (1)