---
# System prepended metadata

title: Map

---

# Map

Design and implement a `threadsafe` map. A key/value datastructure. It has the following properties

*Ofcourse use your own underlying datastructure (not the `map` itself. lol)*

- The keys are of any `comparable` type.
- The values can by of `any` type.
- Type checking is done at `compile-time`
    - For example, consider the map `m = Map<int,int>` (pseudocode)
    - Then, `m.put("string","string")` should fail at compile time.

## Creation

- You instantiate the map with the types of key and value. e.g `NewMap(int,int)` or `NewMap[int,int]()`, etc.. (it's up to you)
- If you like, the map can also take in a capacity argument.

## Get
Get gets a value from the map. `map.get(key)`

- It should return `value, exists` where `exists` is a boolean that is `true` if `value` exists in the map. Otherwise, its false and `value` is the default value for the type.

## Put
Put adds or updates an key/value pair in the map. `map.put(key,value)`
- If the key already exists, it updates its value.
- Else, adds a new pair.
- It does not return anything

## Delete

Delete removes the element associated with the key provided. `map.delete(key)`
- If the key does not exist, `delete` is a `no-op`.
- `delete` does not return anything.

## Length
Length returns the size of the map (the number of elements it contains)

### ForEach
`ForEach` applys the calls the func on every key/value pair in the map.
```go=
m.foreach(func(key,val) bool {
    return true
})`
```
The boolen return determines whether to move to the next iteration or terminate the foreach.


## Functional programming (nice to have)

These are nice to have features

### Keys
`keys` returns a list of the keys in the map
```go=
keys = m.keys()
```

### Values
`values` returns a list of the  values in the map
```go=
vals = m.values()
```

### Select
`Select` accepts a filter function and returns a list of values that pass the filter.
```go=
vals = m.select(func(key,val) bool {
    // filter
    return true
})
```

