Problem overview
The method firstN gets a list of integers nums and a number n, and returns a list with the first n numbers, in the same order. When n is 0 the result is an empty list. The constraints keep n between 0 and the length of nums, so you never have to ask for more items than exist.
Three examples show the range of cases:
nums = [3, 8, 1, 9, 4]andn = 3give[3, 8, 1]. The 9 and the 4 are left out.nums = [5, 6, 7]andn = 0give[].nums = [2, 4]andn = 2give[2, 4], becausenequals the length and every number is kept.
Approach: one slice
A loop that appends items one by one would work, but Python has a tool made for this job: the slice. nums[:n] is a new list that starts at index 0 and stops just before index n. Its items sit at indexes 0 to n - 1, which is exactly n items. The end index is never included, so no - 1 is needed.
The edge cases need no special code. When n is 0 the slice nums[:0] has nothing between the start and the end, so it is an empty list. When n equals len(nums) the slice covers the whole list and gives a copy of it.
Step by step
- Slice
numsfrom the start up to indexnand store the result inresult. With nothing before the colon, the slice starts at index 0. - Return
result. Slicing builds a new list, sonumsitself is left as it was.
The solution in Python
class Solution:
def firstN(self, nums: List[int], n: int) -> List[int]:
result = nums[:n]
return result
Run on the three examples, it prints:
[3, 8, 1]
[]
[2, 4]
The annotations List[int] and -> List[int] only describe the types for the reader. Python does not check them when the code runs. The self parameter belongs to the class and you don't pass it yourself.
Another way: a loop
The same result comes from building the list by hand. It is longer, but it shows what the slice does for you:
def first_n_loop(nums, n):
result = []
for i in range(n):
result.append(nums[i])
return result
range(n) gives the indexes 0 to n - 1, and each pass copies one number. With n = 0 the loop body never runs and the empty result is returned. On the three examples it gives the same lists as the slice: [3, 8, 1], [] and [2, 4]. Because the constraints keep n within the length, nums[i] never goes out of range here. A slice would also forgive an n that was too big, while the loop would raise an IndexError.
Edge cases and common mistakes
- Writing
nums[:n - 1]. That drops one number too many. For the first example it gives[3, 8]. - Writing
nums[n]. One index gives a single number, not a list. Withn = 3it returns9, and withnequal to the length it raises anIndexError. - Using a negative end.
nums[:-1]means "all but the last", counting from the end. The slicenums[:n]counts from the start, which is what the task asks for. - Worrying about
n = 0. Noifis needed.nums[:0]is already[].
Testing
Try the three examples above, and also a list of one number with n = 1 (the result is that same number in a list). If the output is right for n = 0 and for n = len(nums), the ends of the range are right.
