Google Interview Question
1,069 Interview Reviews |
Back to all Google Interview Questions & Reviews
Interview questions and reviews posted anonymously by interview candidates
Interview Question for Software Engineer at Google:
* Describe the design of a most-recently-used list, such as the "Recent Files" menu in Microsoft Word. It has two public methods, getlist() and access(str), which retrieve the list and mark an item as accessed, respectively. The list has a maximum number of items it can hold, say 5, and it should not have duplicates. Describe the data structure used and the running time of both public methods.
Helpful Question?
Yes |
No
Inappropriate?
Answers & Comments (10)
I don't think that will work. first of all, a queue is usually defined as FIFO, so you can only add to the tail of the queue. Secondly, using a queue to check if an item exists will take O(n) time, not O(1) as you suggested. So insertion will take O(n). also using a queue does not guarantee the fixed length. think of the MS example, your first accessed item will eventually get pushed out of the list when you keep accessing new files.
Helpful Answer?
Yes |
No
Inappropriate?
Checking against the stack won't be O(n) since the size of the stack is constant (5). It will be O(1).
Helpful Answer?
Yes |
No
Inappropriate?
He wanted to be sure I covered all 3 logical cases every time I improved my solution towards the final one:
* Returning the sequence in appropriate MRU order
* Maintaining the order at insertion
* Maintaining the maximum list size at insertion
Anonymous, your point about constant size, while technically correct, might feel like a bit of a cop-out in an interview. It's a good observation, but I think I would point it out and then ask if the analysis should assume arbitrary n for the maximum size. Since this is Google, processing infinite streams of data daily, we might assume they want an MRU list that could be used for arbitrary n. In that case I believe we do need a little more machinery than a plain stack or queue.
Helpful Answer?
Yes |
No
Inappropriate?
Helpful Answer?
Yes |
No
Inappropriate?
Did they get back to you with an offer?
Helpful Answer?
Yes |
No
Inappropriate?
Helpful Answer?
Yes |
No
Inappropriate?
0 of 1 people found this helpful
I don't think using either a stack or a map(dictionary if you will) would be a very good solution as maintaining the order would be important in this case. stack must be LIFO, and a map is simply not good for ordering.
A special case must be considered is when an item already exists in the list but not the top, then when this item gets accessed, it should pop to the top while pushing other items down. though none of the elements already in the list should be removed in this case.
in order to maintain order and satisfy the above special case, an array for fixed size or an array-based queue/list would be a better fit. note i specifically said array-based queue as they are easier to sort and manipulate ordering than a linked list. sorting a linked list is simply nightmare.
finally an alternative, and also good solution would be to use a binary search tree structure with the tree sorted based on the access order. this would give pretty good general case performance for both fixed size and arbitrary length.
Helpful Answer?
Yes |
No
Inappropriate?
The basic access(myStr) algorithm:
// Check if str is MRU, O(1)
if (myStr == mru) return;
// Remove LRU, O(1)
tmp = lruStr.successor
tmp.predecessor = null
remove lru from table
lru = tmp
// Check if myStr in table, O(1)
if (myStr in table)
// "Remove" myStr, O(1)
myStr.predecessor.successor = myStr.successor
myStr.successor.predecessor = myStr.predecessor
endif
// Add myStr as head, O(1)
myStr = mruStr.successor
myStr.predecessor = mruStr
mruStr = myStr
Comments, corrections, and advice greatly appreciated.
Helpful Answer?
Yes |
No
Inappropriate?
array is not a good solution either, because it is not easy to remove an item in the middle and insert in the front.
a simple single linked list should do the work. get list is O(1), since you only need to return the head. access(str) is O(n). you travel the list and count how may items you traveled, if you find it (str), just remove it from the list. And if you did not find it right before you hit the end, and if total number of items exceeds the limit, remove the last one. after you travel the list, put the new item in the front.
Helpful Answer?
Yes |
No
Inappropriate?
Members can
answer or comment on this question
–
Join Now (It's Free) or
Sign In
0 of 1 people found this helpful
by Anonymous:
getlist() will return head of queue - O(1)
access(str) will check if str will exist and if not, insert at the head - O(1)
space - O(1)