Implement Single-Tab Browser History Navigation
Implement a BrowserSession for a single-tab browser.
APIs
BrowserSession(homepage)— initialize the session; the current page starts athomepage.visit(url)— navigate tourlfrom the current page and clear any forward history.back(steps)— move up tostepspages back; if fewer pages exist, move as far as possible. Return the current url after the move.forward(steps)— move up tostepspages forward; if fewer pages exist, move as far as possible. Return the current url after the move.haveVisited(url)— return whether the session has ever visitedurlat least once since construction, regardless of whether it currently sits in back/forward history.
Driver contract for this console
In JavaScript, TypeScript, and Python you implement a single function solution(operations, args):
operationsis a list of method-name strings; the first is always"BrowserSession".argsis a parallel list of argument lists, one per operation.- Replay the operations against one
BrowserSessioninstance and return a list of results, one per operation: null for the constructor and forvisit(which return nothing), the resulting url forbackandforward, and the boolean forhaveVisited.
The starter code already contains that replay loop, so only the class body is yours to fill in. In Java, C++, and Go you implement the BrowserSession class alone and the harness replays the operations for you.
Edge cases to handle
steps <= 0(including negative) must not move the cursor.visitmust truncate any forward history before appending the new page.backandforwardpast the ends clamp to the oldest and newest page.haveVisitedis true for every url ever visited (and for the homepage), even after a latervisitdrops that url from the live forward history.
Examples
operations = ["BrowserSession", "visit", "visit", "visit",
"back", "back", "forward", "visit",
"forward", "back", "back"]
args = [["leetcode.com"], ["google.com"],
["facebook.com"], ["youtube.com"], [1], [1], [1],
["linkedin.com"], [2], [2], [7]]
-> [null, null, null, null, "facebook.com", "google.com",
"facebook.com", null, "linkedin.com", "google.com",
"leetcode.com"]After visiting google, facebook, and youtube the cursor sits at youtube. back(1) lands on facebook and back(1) again on google, then forward(1) returns to facebook. Visiting linkedin.com there clears the forward history — youtube is gone — so forward(2) clamps to linkedin, back(2) reaches google, and back(7) clamps to the homepage.
operations = ["BrowserSession", "visit", "visit",
"haveVisited", "haveVisited", "back", "haveVisited"]
args = [["home.com"], ["a.com"], ["b.com"],
["a.com"], ["z.com"], [1], ["b.com"]]
-> [null, null, null, true, false, "a.com", true]a.com was visited so it reports true, while z.com never was. After back(1) lands on a.com, b.com still reports true: the visited set never shrinks.
Constraints
- The first operation is always
BrowserSession(homepage), and the current page always exists. - Urls are non-empty strings.
stepsmay be zero or negative; non-positive steps must not move the cursor.backandforwardclamp at the oldest and newest page rather than erroring.- Target O(1) amortized time per operation and O(n) space for n total visits.
Hints
Hint 1
An array of urls plus a cursor index covers every operation: back and forward are clamped index arithmetic, and visit drops everything after the cursor before appending.
Hint 2
haveVisited cannot read the live history, because visit truncates urls that were still visited. Keep a separate set that only ever grows — written once at construction, then on every visit.
Hint 3
Two stacks or a doubly linked list plus a cursor also work. The array keeps back and forward as pure index math and makes visit's truncation a length change, which is why it is the simplest to justify.