- What are some things we can do to prepare for CS?
- What are some ways to learn a new language?
- Why test code frequently?
- Why isn't official documentation more helpful than Stack Overflow?
- During an interview, what do I do if I can't remember the exact syntax?
- In regard to the code challenge solution, why is the '+' operator being used to concatenate strings? I thought we were supposed to use the join() method in Python?
- How do you get out of the Python built-in
help
? - Are there any helpful VS Code extensions that are recommend for using with Python?
- I'm on Windows; what command do I use to run Python?
- What version of Python do I need?
- How do I get out of the Python REPL?
- What does "REPL" mean?
- I'm on a Mac and when I run Python it says I'm on version 2.7. Why?
- Does Python use tabs or spaces?
- Can you use boolean shortcut assignments?
- Can you do anonymous functions?
- What are all those method names with double underscores around them?
- Where are good Python docs?
- Which linter?
- What's the difference between repr and str?
- How does
sys.argv
work?
- Do I need to use pipenv?
- When do we run pipenv shell?
- How do I get out of the pipenv shell?
- How do I install additional packages from pipenv?
- Is it possible to use system-wide packages from inside the virtual environment?
- Why is there such a debate between OOP and functional programming, and why should we care?
- Following this flow: 1) class Dog is created with attributes size and weight. 2) New instance called Snoopy of class Dog is created. 3) Class Dog gets the method bark() dynamically added to it. Question: will Snoopy now have access to bark() method?
- Can you dynamically add new methods/properties to class through other functions? Or must all properties/methods be declared at once?
- If a subclass inherits from two superclasses with a method of the same name, which method will the subclass use?
- How to handle multiple inheritance and why/when to do it in the first place?
- Does Python have hoisting?
- Does scoping work similar to other languages?
- Can you return a reference to a function from another function? Or store it in a variable?
- Can you do anonymous functions?
- How do I convert an iterator into a list?
- Is a dict like a JavaScript object?
- How do I get a value from a dict?
- Why use tuples instead of lists?
- How do I concatenate two arrays into a single array?
- CS Wiki
- Polya's Problem Solving Techniques
- Solving Programming Problems
- CS Reading List
- How to Google effectively
- How to read specs and code
- Command line primer
- Coding style guidelines
There are a lot of programming paradigms and they all have their strengths and weaknesses when it comes to solving different types of problems.
People can be quite opinionated about their favorites, but it's important to remember that no one language or paradigm is the right tool for all jobs. And, additionally, that virtually all problems can be solved in any of the declarative or imperative paradigms. (Some might produce cleaner, more elegant code for a particular problem.)
Paradigms are the hardest thing to learn because you often have to take all the knowledge you have about solving a problem in another paradigm and throw it out the window. You have to learn new patterns and techniques to be effective.
But we encourage this kind of learning because most popular languages are to some degree multi-paradigm, and the more techniques you know from more paradigms, the more effective you are in that multi-paradigm langage.
In regard to the code challenge solution, why is the '+' operator being used to concatenate strings? I thought we were supposed to use the join() method in Python?
Using join()
to join large numbers of strings is definitely faster in Python
than using the +
operator to do it. The reason is that every time you join()
or use the +
operator, a new string is created. So if you only have to
join()
once, versus using +
hundreds of times, you'll run faster.
That said, if you want to use the join()
approach, you'll have to have all
your strings in a list, which uses more memory than just having the two or three
that you need at a time to use +
. So there's a tradeoff.
Another tradeoff might be in readability. It might be easier to read the +
version. That's worth something.
Finally, if +
is fast enough for this case, it might not be worth the time to
bother with making a list of strings to join()
.
Hit q
for "quit".
It's a common command in Unix "pagers" (programs that show documents a page at a time).
If you're running in PowerShell or cmd, use:
py
If in bash, use python
or python3
.
You should have version 3.7 or higher. Test with:
python --version
You should. Good Python devs know how.
Hit CTRL-D
. This is the way End-Of-File is signified in Unix-likes.
Read, Evaluate, Print Loop.
It reads your input, evaluates it, and prints the result. And loops.
Macs come with version 2.7 by default. You'll need to install version 3.
And preferable use pipenv
after that.
PEP 8 says four spaces.
Cast it:
list(range(5))
produces:
[0, 1, 2, 3, 4]
No.
Generally, and also not really. Variables are either global or function-local.
Since there are no declarations, there's no block-level scope.
It is similar to var
in JavaScript.
Yes. Functions are first-class citizens.
Yes, you can. This is common in Perl and JavaScript, but it's not particularly idiomatic in Python.
x = SomethingFalsey or 5
You can use lambda
for simple functions:
adder = lambda x, y: x + y
adder(4, 5) # 9
do_some_math(4, 5, lambda x, y: y - x)
Sort of.
The syntax is different, though. In Python you must use []
notation to access elements. And you must use "
around the key names.
Those are function you typically don't need to use, but can override or call if you wish.
Most commonly used are:
__init__()
is the constructor for objects__str__()
returns a string representation of the object__repr__()
returns a string representation of the object, for debugging
d = {
"a": 2,
"b": 3
}
print(d["a"])
You don't use dot notation.
pipenv shell
puts you into your work environment. When you're ready to work, or run the code, or install new dependencies, you should be in your pipenv shell.
Type exit
.
pipenv install packagename
This is not recommended.
- Official documentation tutorial and library reference.
The official docs might be hard to read at first, but you'll get used to them quickly
Pylint or Flake8. The latter seems to be a bit more popular.
Can you dynamically add new methods/properties to class through other functions? Or must all properties/methods be declared at once?
You can add them dynamically at runtime, but you have to add them to the class itself:
class Foo():
pass
f = Foo()
Foo.x = 12 # Dynamically add property to class
f.x == 12 # True!
def a_method(self):
print("Hi")
Foo.hi = a_method # Dynamically add method to class
f.hi() # Prints "Hi"
This is not a common thing to see in Python, however.
Following this flow: 1) class Dog is created with attributes size and weight. 2) New instance called Snoopy of class Dog is created. 3) Class Dog gets the method bark() dynamically added to it. Question: will Snoopy now have access to bark() method?
Yes.
If a subclass inherits from two superclasses with a method of the same name, which method will the subclass use?
The answer to this is twofold:
-
Lots of devs and shops frown on multiple inheritance, so maybe just don't do it. (Discussion)
-
As for the order in which methods of the same name are resolved, check out the MRO Algorithm which is what Python uses.
class Base1:
pass
class Base2:
pass
class Derived(Base1, Base2): # Multiple inheritance
pass
Sometimes multiple inheritance can lead to elegant solutions when a subclass needs attributes from multiple, otherwise-unrelated parent classes.
However, a lot of people find it's not worth the trouble) and opt for other solutions, like composition.
- Tuples are immutable. There's a school of thought that says bugs can be reduced if you make as many things immutable as you can.
- Tuples are faster than lists to access.
- Some tuples (containing primitive types), can be used as
dict
keys.
Generally speaking, __repr__
is the string a dev would want to see if they
dumped an object to the screen. __str__
is the string a user would want to see
if the object were print()
ed.
The output of __repr__
should be valid Python code that can reproduce the
object.
class Goat:
def __init__(self, leg_count):
self.leg_count = leg_count
def __repr__(self):
return f'Goat(leg_count={self.leg_count})'
def __str__(self):
return f'a goat with {self.leg_count} legs'
In action:
>>> g = Goat(4)
>>> str(g)
'a goat with 4 legs'
>>> g
Goat(leg_count=4)
>>> Goat(leg_count=4) # output of __repr__ makes a clone of that object!
Goat(leg_count=4)
It's a list that holds command line arguments. This is a way for a user to run your program and specify different behavior from the command line.
Here's a small program that prints the command line arguments:
import sys
for i in range(len(sys.argv)):
print(f'Argument #{i} is: {sys.argv[i]}')
and here's some output, assuming you named the script foo.py
:
$ python foo.py
Argument #0 is: foo.py
$ python foo.py antelope buffalo
Argument #0 is: foo.py
Argument #1 is: antelope
Argument #2 is: buffalo
Note that the 0th element in the list is the name of the program.
Here's another program that prints up to whatever number the user specifies:
import sys
for i in range(int(sys.argv[1])):
print(i+1)
Example runs:
$ python foo.py 2
1
2
$ python foo.py 4
1
2
3
4
Use extend()
.
a = [1, 2, 3]
b = [4, 5, 6]
a.extend(b)
print(a) # [ 1, 2, 3, 4, 5, 6 ]
- Figure out how variables and functions work.
- Build small toy programs to test individual features.
- Build a larger project that exercises many features.
- Don't get frustrated! Treat the problem like a curiosity, a thing to be studied.
- Do small tutorials or code-alongs.
- Find docs you like.
- Learn the differences between this language and one you know.
- Learn this language's way of doing the things you know.
Things to look for in the new language:
- Collections (arrays, vectors, dictionaries)
- Data types
- Iterators
- Flow control (if, while, loops, etc)
- Functions
- etc.
It's often better to make progress in small increments than to write a bunch of stuff and test it in one go.
Also, it's easier to stay motivated if you spend 10 minutes getting a first version going, even if it's missing 99% of its features, and then starting to iterate on that.
Often official documentation is more geared toward being a concise reference. Stack Overflow is more of an example-based learning environment.
Sometimes you need to know the specific details. In those cases, you can dig into the spec, with all it's lawyerly language, and try to decipher what it is you have to do.
Other times, you just need a getting-started example, and Stack Overflow is great for that.
Both types of documentation have their purpose.
Just say so.
"I can't remember how to add an element to the end of the list in Python... is
it push()
? In any case, we'll call the function here that does that."
(Turns out it's append()
in Python, but being honest and describing what it is
your're trying to do will get you 99% of the way there in an interview.)