I have created a concurrent map in golang guarded by Mutex, but still, when two goroutines modify the map, golang panics with concurrent map access and map writes exception, I don’t know what to do more to stop this race condition from happening.
package main
import (
"os"
"fmt"
"io/ioutil"
"strings"
"sync"
)
type concurrentMap struct{
sync.Mutex
urls map[string]int
}
func (c *concurrentMap) addToMap(url string) {
c.Lock()
if val , ok := c.urls[url];ok{
c.urls[url] = val + 1
}else{
c.urls[url] = 1
}
c.Unlock()
}
func NewConcurrentMap() *concurrentMap {
return &concurrentMap{
urls:make(map[string]int),
}
}
func (c *concurrentMap) getUrls() map[string]int {
return c.urls
}
func main(){
c := NewConcurrentMap()
var waitGroup sync.WaitGroup
file_path := os.Args[1]
contents , err := ioutil.ReadFile(file_path)
if err != nil {
fmt.Println(err)
return
}
fileContents := string(contents)
lines := strings.Split(fileContents,"\n")
half := len(lines) / 2
go func(subset []string){
waitGroup.Add(1)
defer waitGroup.Done()
for _,line := range subset {
data := strings.Split(line,",")
if len(data) < 2{
continue
}
url := data[1]
c.addToMap(url)
}
}(lines[0:half])
go func(subset []string){
waitGroup.Add(1)
defer waitGroup.Done()
for _,line := range subset {
data := strings.Split(line,",")
if len(data) < 2{
continue
}
url := data[1]
c.addToMap(url)
}
}(lines[half+1:])
waitGroup.Wait()
fmt.Println(c.getUrls())
}