I am doing the following programming exercise: URL Timestamps. The statement is:
For my web app, I need a class that lets me store timestamps for URLs. For URLs that were never accessed, it should return -1. The class should be able to handle about a million calls in a few seconds.
I have tried:
import java.net.URL;
import java.util.*;
public class UrlMap {
private static final Map<URL,Long> map = new HashMap<URL,Long>();
public void setTimestamp(URL url, long timestamp) {
map.put(url,timestamp);
}
public long getTimestamp(URL url) {
System.out.println("map: "+map);
return map.getOrDefault(url,-1L);
}
}
I have a lot of curiosity because of it does not pass the execution tests but it does pass the example tests. The example tests are:
import static org.junit.Assert.*;
import org.junit.Test;
import java.net.URL;
public class UrlMapTest {
@Test
public void testCodewars() throws Exception {
UrlMap map = new UrlMap();
URL url1 = new URL("http://www.codewars.com/");
long time1 = 12345L;
URL url2 = new URL("http://www.codewars.com/kata/url-timestamps/");
long time2 = 67890L;
map.setTimestamp(url1, time1);
map.setTimestamp(url2, time2);
assertEquals(time1, map.getTimestamp(url1));
assertEquals(time2, map.getTimestamp(url2));
}
@Test
public void testNew() throws Exception {
UrlMap map = new UrlMap();
URL url1 = new URL("http://www.codewars.com/");
URL url2 = new URL("http://www.codewars.com/kata/url-timestamps/");
assertEquals(-1, map.getTimestamp(url1));
assertEquals(-1, map.getTimestamp(url2));
}
}
I will explain the difficulty as best as I can. The execution tests, create a "url1" with timestamp 12345L. Then, in the next tests, it creates a url1 without timestamp. So it would expect to get a -1, because of it should not have a timestamp stored, however it does have the initial timestamp, as the map is static.
As an image worths more than a thousand words:
I think this code passes the example tests because of in each of the test methods a new UrlMap is being created. However, in the execution tests I suppose the exact same urlMap class is being reused.
To try to fix this issue I have read: How can I initialise a static Map? How to update a value, given a key in a hashmap? What is an efficient way to implement a singleton pattern in Java?
How could we store urls and timestamps with a singleton pattern?
EDIT: Following @JoakimDanielson answer we pass the test which previously was been discussed. However it times out, execution time is above 16000ms. How could we improve this code to pass it?
import java.net.URL;
import java.util.*;
public class UrlMap {
private Map<URL,Long> map;
public UrlMap(){
map=new HashMap<URL,Long>();
}
public void setTimestamp(URL url, long timestamp) {
map.put(url,timestamp);
}
public long getTimestamp(URL url) {
return map.getOrDefault(url,-1L);
}
}