Topcoder and Leetcode Problems for Review and Practice
James S. Plank, University of Tennessee
The purpose of this web site is to have a bunch of Topcoder (and Leetcode)
problems for CS140 and CS302
students to go through on their own for practice. In these files, I will give various hints
and perhaps solutions to the problems.
Please email me if you see typos and/or problems with any of these writeups.
Finding the problems on Topcoder
You'll need to create an account at topcoder.com. Then, go to
https://arena.topcoder.com and click on the icon on the
top of the page that says "practice problems" (you have to point the mouse to the icon to see
the text). That will take you to a page with a search bar, and you search for the problem name.
The links in the in the writeups have gotten to the point where they
work only sporadically, so before you give up, go to this link and search for
the problem.
Leetcode
Leetcode is another one of these programming web sites,
like Topcoder, that has been a popular tool for job interviewers. I'll sprinkle in some
Leetcode problems below as well.
Doing these without Topcoder/Leetcode's Servers
As time has gone on, I'm afraid that Topcoder's servers have become unreliable.
I haven't had that problem with Leetcode yet, but you never know.
For that reason, I am going through these writeups, and making sure that you can do the problems
without having to rely on Topcoder/Leetcode's servers working.
The problem
"Cryptography" (SRM 480, D2, 250-Pointer) has a writeup
on how to do the problem without Topcoder's servers, and how to test yourself. Please do that
problem first, when you're starting to practice with these problems. That will help you
form a workflow that works effectively when Topcoder/Leetcode's servers are down.
When I finish
writing up a problem and providing testing information so that you can do it without
the servers, I will color the problem's listing below in red.
D2 250-point Practice Problems
When students ask me what they can do to prepare for CS302 (and even CS140), my response is
always, "Topcoder." The 250-point problems from Division 2 are great in this regard,
because they typically require small (10-line) solutions, and are straightfoward. Your
goal with these problems should be to get them within 20 minutes or so. When you get
better at coding quickly, make that goal 5 minutes!
With these web pages, what you should do is the following:
- Go to topcoder and attempt the problem without reading my help. If you
get it, great! Go on to the next.
- If you are having trouble, especially if you are having trouble getting started or
crafting a solution, then click on the web link and read the help/hints. Then go
back and try it again.
- If this is a problem that I don't assign for labs, I'll try to include a
commented solution. That way, you can compare your code to the code of a seasoned
veteran, and that may help you learn!
I'm going to order these problems from easiest to hardest, using the success rates from
Topcoder as the metric. The S/N designations are whether or not I provide a solution.
- 94.7% - N - SRM 609, D2, 250-Pointer (MagicalStringDiv2). Strings.
- 94.0% - N - SRM 605, D2, 250-Pointer (AlienAndPassword). Strings.
- 93.7% - S - SRM 608, D2, 250-Pointer (OneDimensionalRobotEasy). Simulate a robot with a for loop and three if statements.
- 93.2% - N - SRM 714, D2, 250-Pointer (RangeEncoding). One for loop.
- 92.3% - N - SRM 719, D2, 250-Pointer (LongLiveZhangzj). Inserting strings into a set, and then finding them.
- 92.2% - S - SRM 616, D2, 250-Pointer (WakingUpEasy). Successively run through a vector, subtracting from a value, until it is ≤ 0.
- 91.9% - N - SRM 480, D2, 250-Pointer (Cryptography). Sort and use long long's.
- 91.7% - S - SRM 702, D2, 250-Pointer (TestTaking). Some subtraction and some tertiary expressions.
- 89.2% - N - SRM 603, D2, 250-Pointer (MiddleCode) - Strings, and evaluating two solutions to a simple problem.
- 89.2% - N - SRM 734, D2, 250-Pointer (TheRoundCityDiv2).
Do a brain-dead nested for loop and count.
- 88.4% - N - SRM 603, D7, 250-Pointer (BoundingBox) - Graph some points to figure out the answer.
- 88.1% - N - SRM 564, D2, 250-Pointer (FauxPalindromes). Practice with strings.
- 87.1% - S - SRM 698, D2, 250-Pointer (Initials). A three-line practice problem with strings.
- 86.6% - N - SRM 708, D2, 250-Pointer (SafeBetting).
Simple simulation.
- 86.2% - S - SRM 695, D2, 250-Pointer (BearNSWE).
Maintaining the Bear's (x,y) coordinate, and then using the distance formula.
- 85.8% - S - SRM 697, D2, 250-Pointer (TriangleMaking). Reasoning about a triangle, and using sorting to make your life easier.
- 85.6% - N - SRM 704, D2, 250-Pointer (SwapAndArithmetic). Sort and traverse.
- 85.5% - S - SRM 673, D2, 250-Pointer (BearSong). Create a map and traverse it.
- 85.3% - N - SRM 469, D2, 250-Pointer (ShorterSuperSum). Very simple recursion.
- 83.2% - N - SRM 666, D2, 222-Pointer (DevuAndGame).
Simulate a really easy game.
- 82.4% - N - SRM 722, D2, 250-Pointer (HillClimber).
Run through a vector and keep track of stuff.
- 80.0% - S - SRM 705, D2, 250-Pointer (SuperUserDo).
Simulate and count.
- 79.0% - S - TCO 2016, Q1A, 250-Pointer (EllysTimeMachine). Sscanf() and sprintf().
- 77.9% - N - SRM 707, D2, 250-Pointer (Cross). Processing a vector of strings.
- 77.7% - N - SRM 706, D2, 250-Pointer (ThreeIncreasing). Thinking about a problem in the correct order.
- 73.9% - N - SRM 700, D2, 250-Pointer (Xylophone). Mod.
- 72.0% - N - SRM 686, D2, 250-Pointer (TreeAndVertex). Count edges coming out of nodes of a tree.
- 71.0% - S - SRM 688, D2, 250-Pointer (ParenthesesDiv2Easy). Run through a string and maintain a counter.
- 70.9% - N - TCO 2017, Q1A, 250-Pointer (PingPongQueue). Simulate a simple system.
- 70.1% - N - SRM 736, D2, 250-Pointer (A0Paper). Run through a vector backward.
- 69.8% - S - SRM 691, D2, 300-Pointer (Plusonegame).
Counting digits and building a return string.
- 69.8% - N - SRM 499, D2, 250-Pointer (SimpleGuess). Using a set and a simple enumeration of (X,Y) pairs.
- 68.7% - N - SRM 701, D2, 250-Pointer (SquareFreeString). Simple enumeration and substrings.
- 68.4% - N - SRM 604, D2, 250-Pointer (FoxAndWord). Simple enumeration and .substr().
- 68.4% - N - SRM 718, D2, 250-Pointer (RelativeHeights). Maps, sets and some string processing.
- 66.7% - N - SRM 730, D2, 250-Pointer (IntervalIntersections). Determine if two intervals intersect.
- 66.1% - S - SRM 699, D2, 250-Pointer (UpDownHiking). Keep track of two values per day for N days.
- 65.8% - N - SRM 689, D2, 250-Pointer (SimilarUserDetection). Strings and sets.
- 64.3% - N - SRM 587, D2, 250-Pointer (InsertZ). Strings and problem solving.
- 63.0% - S - SRM 741, D2, 250-Pointer (DigitStringDiv2). Enumerating substrings and converting them to integers.
- 62.4% - S - SRM 696, D2, 250-Pointer (Ropestring).
Counting rope lengths, and then using them to create a return string.
- 60.4% - N - SRM 683, D2, 250-Pointer (EqualSubstrings2). Strings.
- 60.4% - N - SRM 720, D2, 250-Pointer (DistinctGridEasy). Using a set to count distinct elements.
- 60.2% - S - TCO 2017, Q1B, 250-Pointer (WaterAndOxygen). Algebra.
- 59.3% - N - SRM 643, D2, 250-Pointer (TheKingsArmyDiv2). Using the find() method for strings, and running though the characters in a vector of strings.
- 59.3% - N - Leetcode 783: Minimum Distance Between BST Nodes. Postorder tree traversal.
- 57.9% - N - SRM 350, D2, 250-Pointer (DistanceBetweenStrings). Strings.
- 57.3% - N - SRM 610, D2, 250-Pointer (DivideByZero). An O(n2) loop doing O(1) work.
- 57.2% - N - SRM 739, D2, 250-Pointer (HungryCowsEasy). Using lower_bound() on a map.
- 57.0% - S - SRM 597, D2, 250-Pointer (LittleElephantAndDouble). Multiple ways to do a problem.
- 54.3% - S - Leetcode 953: Verifying an Alien Dictionary. Setting up a translation of one string to another so you can use C++'s string comparison.
- 52.3% - S - SRM 679, D2, 250-Pointer (ListeningSongs).
Break the problem into parts, and use sort() to help you.
- 52.0% - S - SRM 663, D2, 250-Pointer (ChessFloor). Enumerate two letters and run through a two-dimensional vector.
- 49.1% - S - SRM 729, D2, 250-Pointer (BrokenChessboard). Two for loops and a mod.
- 48.4% - S - SRM 717, D2, 250-Pointer (NiceTable). You'll be tempted to try to be smart, but instead, look at the constraints and do two power set enumerations.
- 47.4% - S - SRM 693, D2, 250-Pointer (TriangleEasy). This is a simple O(n3) enumeration, but you have to use the right O(n3) enumeration.
- 46.3% - N - SRM 623, D2, 250-Pointer (CatchTheBeatEasy). Create a multimap and traverse it.
- 44.6% - S - SRM 183, D2, 350-Pointer (CountGame). You'll
want to think of game strategy, but if you simply use dynamic programming, you'll get the answer quickly!
- 44.0% - N - SRM 583, D2, 250-Pointer (SwappingDigits). A simple solution works, but you can make it much faster if you think it through a little more.
- 43.9% - N - SRM 606, D2, 250-Pointer (EllysSubstringSorter). Gives you practice with the substr() method, and sort().
- 40.4% - N - Leetcode problem - Maximum Area of a Piece of Cake After Horizontal and Vertical Cuts. Sort and find some max's. Not sure why it's 40.4% (and was a "medium").
- 39.8% - S - SRM 709, D2, 250-Pointer (RoboFactory). Thinking precisely.
- 34.2% - N - Leetcode problem 134 - Gas Station. Using graphics to think through a problem.
D1 250-point Problems (or D2 500-point Problems or Leetcode Mediums)
These are harder than the problems above, and often fit into some class of algorithm
from CS202 or CS302. The percentages for the D2, 500-pointers are much lower than
the D1, 250 pointers for two reasons: First, the programmers in D1 are better. Second,
by the time the D2 programmers get to the 500-point problem, they may not have time to
complete it. Keep that in mind.
- 88.9% - N - SRM 814, D1, 250-Pointer (StepLeapSurviveTraps). Multimap
- 83.0% - N - SRM 790, D1, 250-Pointer (TheSocialNetwork). Graph connectivity.
- 77.2% - N - SRM 736, D1, 250-Pointer (DigitRotation). Strings and math.
- 77.2% - N - SRM 722, D1, 250-Pointer (TCPhoneHome). String/Number manipulation and maps.
- 74.2% - N - SRM 619, D1, 250-Pointer (SplitStoneGame). A straightforward dynamic program.
- 74.0% - N - Leetcode #1396 Design Underground System. Unordered maps
- 73.3% - N - SRM 590, D1, 250-Pointer (FoxAndChess). Vectors and Strings.
- 72.6% - N - SRM 728, D1, 250-Pointer (Halving). Maps, recursion.
- 72.4% - N - Leetcode #406: Queue Reconstruction by Height. Can you do better than O(n2)?
- 71.3% - S - Leetcode #695: Max Area of Island. DFS for connected components.
- 71.2% - N - Leetcode #22: Generate Parentheses. Enumeration.
- 70.2% - N - SRM 468, D1, 250-Pointer (T9). Create a map, whose vals are vectors of strings. Parse a string and create a return value.
- 70.0% - N - SRM 685, D1, 250-Pointer (MultiplicationTable2). A couple sets and a vector.
- 68.2% - N - SRM 737, D1, 250-Pointer (AliceAndBobEasy). Either you know the Sprague-Grundy theorem or you don't. Once you do, then this
is a nice practice problem with bit arithmetic.
- 68.5% - S - SRM 478, D1, 250-Pointer (CarrotJumping). BFS.
- 67.5% - S - Leetcode #2477: Minimum Fuel Cost to Report to the Capital. Postorder tree traversal.
- 67.0% - S - Leetcode problem: "Search-Suggestions-System". Sets or lists -- it's a nice exercise in runtime analysis.
- 66.5% - N - SRM 621, D1, 275-Pointer (RadioRange). Maps.
- 65.9% - S - SRM 612, D1, 250-Pointer (EmoticonsDiv1). I solve this as a classic Breadth-First Search, where you create the graph as you process the BFS queue.
- 63.1% - S - TCO 2008, Q3, 500-Pointer (CableDonation). Minimum Spanning Tree.
- 63.1% - S - TCO 2017, Q1A, 500-Pointer (CheeseSlicing). Dynamic programming.
- 62.9% - S - SRM 702, D1, 300-Pointer (GridSortMax). A greedy algorithm on vectors.
- 61.1% - S - Leetcode 129: Sum Root To Leaf Numbers. Preorder tree traversal
- 59.8% - N - SRM 739, D1, 250-Pointer (ForumPostEasy). Simple enumeration.
- 59.5% - N - TCCO Qualification Round 1, 500-Pointer (LandMines). DFS.
- 59.5% - N - SRM 596, D2, 500-Pointer (ColorfulRoad). Good practice for Dijkstra's Algorithm, Dynamic Programming or Toplogical Sort.
- 59.0% - N - SRM 382, D1, 250-Pointer (CollectingRiders). BFS.
- 58.8% - N - Leetcode problem: "Single Element In A Sorted Array". Binary search.
- 57.2% - S - Leetcode problem: "Lowest-Common-Ancestor". Postorder tree traversal.
- 57.1% - N - Leetcode problem: "My Calendar I". lower_bound() on a map.
- 57.0% - N - TCO 2016 Round 1A, 500-Pointer (EllysSocks). Straightforward Dynamic Program.
- 54.7% - S - SRM 727, D1, 250-Pointer (OnlySanta). Logic.
- 53.5% - N - SRM 183, D2, 550-Pointer (BridgeSort). Simple sorting.
- 53.5% - S - SRM 686, D1, 250-Pointer (BracketSequenceDiv1). Dynamic programming, plain and simple.
- 52.7% - S - Leetcode problem: "Triangle". Dynamic programming all the way through step 4!
- 52.7% - N - SRM 731, D1, 250-Pointer (TreesAndBrackets). Recursion on a tree. This writeup is meant to help CS202 students
with both trees and recursion.
- 52.2% - N - Leetcode #1239: Maximum Length of a Concatenated String with Unique Characters. Bit arithmetic and enumeration.
- 51.9% - S - TCO 2015 Round 1A, 250-pointer (Similars).
Gives you good practice using bits as sets.
- 50.8% - N - Leetcode problem 990: "Satisfiability of Equality Equations". Disjoint sets.
- 50.7% - N - SRM 730, D1, 250-Pointer (StonesOnATree).
Postorder tree traversal, plus some thought.
- 50.5% - N - SRM 733, D1, 250-Pointer (MinimizeAbsoluteDifferenceDiv1). Using next_permutation() and avoiding a pitfall.
- 49.7% - N - SRM 706, D2, 500-Pointer (SellingFruits). Binary Search and avoiding pitfalls.
- 49.6% - S - SRM 700, D1, 300-Pointer (FindingFriend). Running through a vector and maintaining the correct information to solve the problem.
- 49.4% - N - SRM 741, D1, 250-Pointer (DigitStringDiv1). Dynamic programming.
- 48.7% - N - SRM 486, D1, 300-Pointer (OneRegister). BFS.
- 48.5% - S - SRM 614, D1, 250-Pointer (MinimumSquare). Inclusion / Exclusion Principle. I go over this problem in my CS494 class. These are the lecture notes. It's one of those problems that I beat to death. Sorry.
- 47.9% - N - Leetcode #316 - Remove Duplicate Letters. Reasoning, using bits as sets.
- 47.8% - N - SRM 740, D1, 250-Pointer (RainForecast). Probability -- easy programming.
- 47.0% - S - SRM 708, D2, 500-Pointer (BuildingStrings). Iteratively solving a problem with strings.
- 46.4% - S - Leetcode problem 1696: "Jump-Game-VI". Dynamic programming and a multiset.
- 46.1% - N - Leetcode problem 2300: "Successful-Pairs-Of-Spells". You can use a map, binary search, or sorting.
- 46.1% - N - SRM 671, D1, 250-Pointer (BearCries). Dynamic programming.
- 44.7% - N - SRM 734, D1, 250-Pointer (TheRoundCityDiv1). Prime factoring, power set enumeration, thinking.
- 43.0% - S - SRM 604, D2, 500-Pointer (PowerOfThreeEasy). I solve this using a power set enumeration, and teach this in CS302.
- 42.2% - N - Leetcode #1996: The Number of Weak Characters in the Game. Leveraging Sorting.
- 41.6% - S - SRM 699, D1, 250-Pointer (OthersXor).
Nice problem to practice bits and thinking about XOR's.
- 40.6% - N - SRM 564, D2, 500-Pointer (TheBrickTowerMediumDivTwo).
- 40.5% - N - Leetcode #393: UTF-8-Validation. Bit arithmetic.
- 40.5% - N - Leetcode #307: Range Sum Query - Mutable. Building and using a balanced binary tree.
Enumeration
- 39.9% - S - SRM 714, D2, 500-Pointer (RemovingParenthesis).
A straightforward dynamic programming counting problem.
- 39.3% - N - SRM 701, D1, 250-Pointer (PartisanGame).
Dynamic Programming.
- 38.7% - N - Leetcode problem - Non-Negative Integers Without Consecutive Ones. Bits and you can practice DP too if you want.
- 38.5% - N - SRM 738, D1, 250-Pointer (FindThePerfectTriangle).
- 38.0% - N - SRM 817, D2, 500-Pointer (Gym). Multisets.
- 37.9% - N - SRM 592, D2, 500-Pointer (LittleElephantAndPermutationDiv2). Reasoning about permutations.
- 37.2% - N - Leetcode #50: Pow(x,n). Bit arithmetic.
- 37.2% - S - SRM 641, D1, 250-Pointer (TrianglesContainOrigin).
Geometry and Maps. I walk through the solution in my CS494 class and include the presentation here.
- 36.8% - S - SRM 721, D1, 250-Pointer (RememberWords). A little logic; a little math; a binary search instead of algebra.
- 34.7% - S - SRM 682, D2, 550-Pointer (TopBiologist). A Div/Mod enumeration.
- 32.8% - S - SRM 699, D2, 500-Pointer (LastDigit). Dynamic programming with big integers.
- 32.5% - S - SRM 695, D1, 300-Pointer (BearPasswordLexic). Turn a vector into a map, and a map into a string.
- 30.0% - N - SRM 705, D2, 500-Pointer (AlphabetOrderDiv2). Either Topological Sort, or DFS on a directed graph.
- 28.9% - N - SRM 347, D1, 250-Pointer (Aircraft). Either use calculus, or a really neat binary search.
- 25.0% - S - SRM 686, D2, 500-Pointer (SegmentsAndPoints). This is not a hard problem. I suspect the low scores were due to time constraints from the 250-point problem.
- 22.0% - N - SRM 691, D1, 300-Pointer (Sunnygraphs). The coding here is not bad -- a simple DFS that does not even have to be recursive. The hard part is turning that into a solution. This is a nice problem to make you think precisely about graphs.
- 20.0% - S - SRM 344, D2, 500-Pointer (SimpleRotationDecoder). A Div/Mod enumeration plus string manipulation.
- 19.9% - S - SRM 700, D2, 500-Pointer (XMarksTheSpot). Power set enumeration.
- 16.9% - S - SRM 707, D2, 500-Pointer (StepsConstruct). Breadth First Search.
D1 500-point Problems (or D2 1000-point Problems or Leetcode Hard Problems)
For these, I rank them by (number correct / number opened), but I also
report (number correct / number submitted). It's hard to gauge these, again, because it's
hard to know how much time a competitor had when he/she opened the problem. There is also
the issue that with some of these programs, programming up the solution is really easy once
you've figured out the solution, so the second numbers will be pretty high, even though the
problem is hard.
With Leetcode, I simply put question marks in the (number correct / number opened), because Leetcode
only reports (number correct / number submitted).
- ?? / 62.2% - S - Leetcode problem - Paint-House-III. Dynamic programming.
- ?? / 59.3% - N - Leetcode problem - Sum-Of-Distances-in-Tree. Tree Traversals.
- ?? / 52.5% - N - Leetcode problem - Reverse-Nodes-In-K-Group. Manipulating singly linked lists, and recursion.
- 50.3% / 60.9% - N - SRM 740, D1, 500-Pointer (DieDesign). Dynamic programming.
- 47.4% / 93.2% - N - SRM 699, D1, 500-Pointer (FromToDivisible). This is a BFS problem where you have to convert their graph to a tractable one using GCD().
- ?? / 44.4% - S - Leetcode problem - Vertical Order Traversal of a Binary Tree. DFS and Maps.
- ?? / 42.7% - S - Leetcode problem - K Inverse Pairs. Dynamic programming, plus some extra thought.
- ?? / 39.5% - N - Leetcode problem - Maximum Gap. Bucket sort, plus a little thought.
- ?? / 36.2% - N - Leetcode problem - Word-Ladder-I. BFS where you have to pay attention to how you create your adjacency lists.
- ?? / 35.3% - S - Leetcode problem - Palindrome-Pairs. Tries or Hashing - Your pick.
- ?? / 34.7% - N - Leetcode problem - Median of Two Sorted Arrays. Nested Binary Search.
- 29.8% / 80.9% - N - SRM 720, D1, 500-Pointer (Subgraphs). Thinking recursively about graphs.
- ?? / 28.5% - N - Leetcode problem - Substring with Concatenation of All Words. Hashing plus data structures from the STL.
- 26.8% / 87.2% - N - SRM 647, D1, 500-Pointer (CtuRobots). Dynamic Programming.
- 24.9% / 48.0% - N - SRM 383, D1, 500-Pointer (Floorboards). Enumeration.
- 19.1% / 21.5% - N - SRM 729, D1, 450-Pointer (FrogSquare). BFS where you need to only consider a subset of the graph to make it tractible.
- 14.6% / 25.3% - N - SRM 727, D1, 600-Pointer (GroupTheNumbers). Some reasoning, and writing some large-number arithmetic.
- 10.4% / 64.6% - N - SRM 621, D1, 500-Pointer (TreesAnalysis). Topological sort.
- 13.1% / 43.4% - N - SRM 734, D1, 400-Pointer (CardCounter). Dynamic programming.
- 12.0% / 61.4% - N - SRM 470, D2, 1000-Pointer (ActivateGame). Minimum spanning tree.
- 11.3% / 62.9% - N - SRM 713, D1, 500-Pointer (DFSCount). DFS, Dynamic programming and bit arithmetic.
- 7.1% / 52.5% - N - SRM 652, D1, 500-Pointer (MaliciousPath). Fun with Dijkstra's algorithm.
- 6.8% / 44.7% - S - SRM 348, D2, 1000-Pointer (IncreasingSubsequences). I use this as an example when I teach
Topological Sort in CS302.
- 5.9% / 61.1% - S - SRM 702, D2, 1000-Pointer (SubsetSumExtreme). Dynamic programming with bit arithmetic. How can it get any better than that?
- 5.7% / 61.1% - N - 2008 TCO Q2 1000-Pointer (BlackWhiteRectangles). Maps and some bit arithmetic.
- 4.1% / 26.3% - S - TCO 2007, Q1, 1000-Pointer (Alarmed). Converting a problem to a graph, and then doing DFS on it.
- 3.3 / 33.9% - N - TCO 2017, Q1A, 1000-Pointer (PolygonRotation). This is a problem that makes you reason about geometry. My solution relied on line intersection, plus maps. There's nothing here that a CS302 student cannot solve -- you just have to work through it step by step.
- 1.8 / 23.80% - N - SRM 682, D2, 1000-Pointer (FriendlyRobot). Dynamic Programming.
- 0.35 / 20.0% - N - SRM 594, D2, 1000-Pointer (FoxAndGo2). DFS (plus a little thinking)