diff --git a/README.md b/README.md index f201dbf..f8e350d 100644 --- a/README.md +++ b/README.md @@ -12,7 +12,7 @@ or very little programming experience. If you have programmed a lot in the past using some other language you may want to read [the official tutorial](https://docs.python.org/3/tutorial/) instead. -You can use Python 3.5 or any newer Python with this tutorial. **Don't +You can use Python 3.6 or any newer Python with this tutorial. **Don't use Python 2 because it's no longer supported.** ## List of contents @@ -35,7 +35,7 @@ to learn more about whatever you want after studying it. 9. [Handy stuff with strings](basics/handy-stuff-strings.md) 10. [Lists and tuples](basics/lists-and-tuples.md) 11. [Loops](basics/loops.md) -12. [Trey Hunner: zip and enumerate](basics/trey-hunner-zip-and-enumerate.md) +12. [zip and enumerate](basics/zip-and-enumerate.md) 13. [Dictionaries](basics/dicts.md) 14. [Defining functions](basics/defining-functions.md) 15. [Writing a larger program](basics/larger-program.md) @@ -67,7 +67,7 @@ than complex. - **Important:** [getting help](getting-help.md) - [Contact me](contact-me.md) -- Answers for excercises in [basics](basics/answers.md) and +- Answers for exercises in [basics](basics/answers.md) and [advanced](advanced/answers.md) sections - [The TODO list](TODO.md) @@ -109,9 +109,10 @@ See [github's contributors page](https://github.com/Akuli/python-tutorial/graphs *** -If you have trouble with this tutorial please [tell me about -it](./contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](./contact-me.md) and I'll make this tutorial better, +or [ask for help online](./getting-help.md). +If you like this tutorial, please [give it a star](./README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/TODO.md b/TODO.md index 53b2bc3..ff1ecde 100644 --- a/TODO.md +++ b/TODO.md @@ -40,9 +40,10 @@ This tutorial is not complete. It still needs: *** -If you have trouble with this tutorial please [tell me about -it](./contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](./contact-me.md) and I'll make this tutorial better, +or [ask for help online](./getting-help.md). +If you like this tutorial, please [give it a star](./README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/advanced/README.md b/advanced/README.md index cfa964c..bbb46e5 100644 --- a/advanced/README.md +++ b/advanced/README.md @@ -8,7 +8,7 @@ section. Most of the techniques explained here are great when you're working on a large project, and your code would be really repetitive without these things. -You can experient with these things freely, but please **don't use these +You can experiment with these things freely, but please **don't use these techniques just because you know how to use them.** Prefer the simple techniques from the Basics part instead when possible. Simple is better than complex. @@ -20,9 +20,10 @@ than complex. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/advanced/answers.md b/advanced/answers.md index d6a4371..ca52c7f 100644 --- a/advanced/answers.md +++ b/advanced/answers.md @@ -1,9 +1,10 @@ *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/advanced/datatypes.md b/advanced/datatypes.md index 74df310..456d777 100644 --- a/advanced/datatypes.md +++ b/advanced/datatypes.md @@ -347,9 +347,10 @@ do it before Python supported `{**dict1, **dict2}`. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/advanced/functions.md b/advanced/functions.md index 6accb1e..8f54e60 100644 --- a/advanced/functions.md +++ b/advanced/functions.md @@ -50,7 +50,7 @@ For example, instead of this... ```python def get_new_info(username): - print("Changing user information of %s." % username) + print(f"Changing user information of {username}.") username = input("New username: ") password = input("New password: ") fullname = input("Full name: ") @@ -66,7 +66,7 @@ class User: # them here def change_info(self): - print("Changing user information of %s." % self.username) + print(f"Changing user information of {self.username}.") self.username = input("New username: ") self.password = input("New password: ") self.fullname = input("Full name: ") @@ -290,9 +290,10 @@ does, so using keyword-only arguments makes sense. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/advanced/iters.md b/advanced/iters.md index 3be970e..450e763 100644 --- a/advanced/iters.md +++ b/advanced/iters.md @@ -74,7 +74,7 @@ twice. >>> ``` -We have also used [enumerate](../basics/trey-hunner-zip-and-enumerate.md) +We have also used [enumerate](../basics/zip-and-enumerate.md) before, and it actually remembers its position also: ```python @@ -463,9 +463,10 @@ does the same thing as our `count()`. contains many useful iterator-related things. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/advanced/magicmethods.md b/advanced/magicmethods.md index c7f6e28..c333bbe 100644 --- a/advanced/magicmethods.md +++ b/advanced/magicmethods.md @@ -112,13 +112,10 @@ the message is 'hello' Combining `repr()` with [string formatting](../basics/handy-stuff-strings.md#string-formatting) is also -easy. `%` formatting has a `%r` formatter, and `.format()` formatting -has a `!r` flag. +easy. ```python ->>> print("the message is %r" % (message,)) -the message is 'hello' ->>> print("the message is {!r}".format(message)) +>>> print(f"the message is {repr(message)}") the message is 'hello' >>> ``` @@ -155,8 +152,7 @@ follow one of these styles: ... self.name = name ... self.founding_year = founding_year ... def __repr__(self): - ... return 'Website(name=%r, founding_year=%r)' % ( - ... self.name, self.founding_year) + ... return f'Website(name={repr(self.name)}, founding_year={repr(self.founding_year)})' ... >>> github = Website('GitHub', 2008) >>> github @@ -174,8 +170,7 @@ follow one of these styles: ... self.name = name ... self.founding_year = founding_year ... def __repr__(self): - ... return '' % ( - ... self.name, self.founding_year) + ... return f'' ... >>> github = Website('GitHub', 2008) >>> github @@ -235,9 +230,10 @@ are not meant to be imported. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/README.md b/basics/README.md index 24f8547..23d1059 100644 --- a/basics/README.md +++ b/basics/README.md @@ -17,7 +17,7 @@ to learn more about whatever you want after studying it. 9. [Handy stuff with strings](handy-stuff-strings.md) 10. [Lists and tuples](lists-and-tuples.md) 11. [Loops](loops.md) -12. [Trey Hunner: zip and enumerate](trey-hunner-zip-and-enumerate.md) +12. [zip and enumerate](zip-and-enumerate.md) 13. [Dictionaries](dicts.md) 14. [Defining functions](defining-functions.md) 15. [Writing a larger program](larger-program.md) @@ -30,9 +30,10 @@ to learn more about whatever you want after studying it. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/answers.md b/basics/answers.md index 7b53969..766ec70 100644 --- a/basics/answers.md +++ b/basics/answers.md @@ -25,7 +25,7 @@ isn't exactly like mine but it works just fine it's ok, and you can `print('You entered:', something)`. 2. The broken code has mostly the same issues as exercise 1. Here are - the problems that excercise 1 doesn't have: + the problems that exercise 1 doesn't have: - The if-elif-else has a blank line at a confusing place. Delete it. - After deleting the code, it looks quite dense. Add a new blank @@ -100,16 +100,7 @@ isn't exactly like mine but it works just fine it's ok, and you can just fine if we run it, but there's a problem. The last line is really long and it's hard to see what it does. - The solution is string formatting. At the time of writing this, I - recommend replacing the last line with one of these: - - ```python - print("You entered %s, %s, %s and %s." % (word1, word2, word3, word4)) - print("You entered {}, {}, {} and {}.".format(word1, word2, word3, word4)) - ``` - - In the future when most people will have Python 3.6 or newer, you - can also use this: + The solution is string formatting. I recommend replacing the last line with this: ```python print(f"You entered {word1}, {word2}, {word3} and {word4}.") @@ -473,9 +464,10 @@ isn't exactly like mine but it works just fine it's ok, and you can *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/classes.md b/basics/classes.md index 3c1f27d..0b2a284 100644 --- a/basics/classes.md +++ b/basics/classes.md @@ -416,9 +416,10 @@ print("You entered " + word + ".") *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/defining-functions.md b/basics/defining-functions.md index ebe9e12..9b78b94 100644 --- a/basics/defining-functions.md +++ b/basics/defining-functions.md @@ -453,7 +453,7 @@ howdy hi Typing `say_hi` just gives us the value of the `say_hi` variable, which is the function we defined. But `say_hi()` **calls** that function, so it runs and gives us a return value. The return value is None so the -`>>>` prompt [doesn't show it](#variables.md#none). +`>>>` prompt [doesn't show it](variables.md#none). But we know that the print function shows None, so what happens if we wrap the whole thing in `print()`? @@ -510,7 +510,7 @@ colors = ['red', 'yellow', 'blue', 'green', 'orange', 'pink', 'black', 'gray', 'white', 'brown'] choice = ask_until_correct("What's your favorite color?", colors, error_message="I don't know that color.") -print("Your favorite color is %s!" % choice) +print(f"Your favorite color is {choice}!") ``` ## Summary @@ -572,9 +572,10 @@ Answers for the first, second and third exercise are *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/dicts.md b/basics/dicts.md index 9784c5d..597d1eb 100644 --- a/basics/dicts.md +++ b/basics/dicts.md @@ -324,13 +324,14 @@ Running the program might look like this: *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See [LICENSE](../LICENSE). -[Previous](trey-hunner-zip-and-enumerate.md) | [Next](defining-functions.md) | +[Previous](zip-and-enumerate.md) | [Next](defining-functions.md) | [List of contents](../README.md#basics) diff --git a/basics/docstrings.md b/basics/docstrings.md index 7158bb3..c30cd7c 100644 --- a/basics/docstrings.md +++ b/basics/docstrings.md @@ -350,9 +350,10 @@ doing without having to read through all of the code. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/editor-setup.md b/basics/editor-setup.md index ccf71ce..be13ea5 100644 --- a/basics/editor-setup.md +++ b/basics/editor-setup.md @@ -13,9 +13,8 @@ like automatically displaying different things with different colors, but also highlighting mistakes in the code, and coloring syntax. If you are on Windows or Mac OSX you have probably noticed that your -Python came with an editor called IDLE. We are not going to use it -because it's lacking some important features, and most experienced -programmers (including me) don't use it or recommend it. +Python came with an editor called IDLE. You can use IDLE, but we recommend exploring other options first. + ## Which editor? @@ -23,38 +22,48 @@ The choice of an editor is a very personal thing. There are many editors, and most programmers have a favorite editor that they use for everything and recommend to everyone. -If you aren't sure about which editor you should use, I recommend -Porcupine. It's a simple editor I wrote in Python; it lets you edit -files and it doesn't have too many other featues. [Install it with these -instructions](https://github.com/Akuli/porcupine/#installing-porcupine), -and then [learn to use it by writing the classic Hello World -program](https://github.com/Akuli/porcupine/wiki/First-Program). Then -you can [skip the rest of this chapter](#editor-or--prompt). - -Note that most other editors come with settings that are not suitable -for writing Python code. _**TODO:** add a link to the old editor setup -tutorial here._ - -Most of these editors lack some important features, they have so many -features that confuse people or they aren't free. You can use these -editors if you like them, but **these editors are BAD for getting -started with programming**: - -- PyCharm -- IDLE -- Emacs -- Gedit -- Nano -- NetBeans -- Notepad -- Pluma -- Spyder -- Vim -- Wingware - -This list doesn't contain all bad editors, but these are editors that -people often try to use. If you know a bad editor and you think I should -mention it here, please [let me know](../contact-me.md). +The editors can be broadly divided into three categories: + +#### The Basic Text Editors +These editors usually come with the operating system. They do not have features like +running code, auto-completion, etc. that make programming easier. They are usually used for relatively simple +text editing. Most programmers do not use these editors for programming. + +A few popular ones in this category are: +- Notepad (Windows) +- Gedit (Linux) +- Notepad ++ (Windows) +- Nano (Linux/Mac OS) + +#### Smart Text Editors +The text editors in this category have features like auto-completion, syntax highlighting, +running and debugging code, highlighting errors, etc. They are relatively easy to learn and have the necessary features +to start your programming journey. + +A few popular ones in this category are: +- Visual Studio Code / VS Code (Windows/Linux/Mac OS) +- IDLE (Usually comes with Python) (Windows/Linux/Mac OS) +- Thonny (Windows/Linux/Mac OS) +- [Porcupine](https://github.com/Akuli/porcupine) (created by the author of this tutorial) (Windows/Linux/Mac OS) +- Geany (Windows/Linux/Mac OS) + +**We recommend that you look into a few of these editors and install your favorite one.** + +#### IDEs and advanced editors +This category of text editors are usually professional grade pieces of software. They are mostly proprietary and paid. They have a steep +learning curve because of how many features they have. +These types of editors are generally not preferred +in the beginning stage. They are meant to be used for writing complex and large pieces of software. + +A few popular ones in this category are: +- Visual Studio (Not be confused with *Visual Studio Code*) (Windows) +- Pycharm (Windows/Linux/Mac OS) +- Vim (Windows/Linux/Mac OS) +- Emacs (Windows/Linux/Mac OS) + +As already mentioned, there are no "right" or "wrong" editors. The preference of an editor +is a personal choice and we recommend trying different editors. +The lists on this page don't contain all editors, but just a few of the most popular ones. ## Editor or `>>>` prompt? @@ -78,9 +87,10 @@ echoes it back, but if you make a file that contains nothing but a *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/exceptions.md b/basics/exceptions.md index 4ca3603..785fb18 100644 --- a/basics/exceptions.md +++ b/basics/exceptions.md @@ -249,9 +249,9 @@ text = input("Enter a number: ") try: number = int(text) except ValueError: - print("'%s' is not a number." % text, file=sys.stderr) + print(f"'{text}' is not a number.", file=sys.stderr) sys.exit(1) -print("Your number doubled is %d." % (number * 2)) +print(f"Your number doubled is {(number * 2)}.") ``` ## Raising exceptions @@ -452,7 +452,7 @@ def greet(): try: greet() except OSError: - print("Cannot read '%s'!" % filename, file=sys.stderr) + print(f"Cannot read '{filename}'!", file=sys.stderr) if askyesno("Would you like to create a default greeting file?"): with open(filename, 'w') as f: print(default_greeting, file=f) @@ -461,9 +461,10 @@ except OSError: *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/files.md b/basics/files.md index 82705d0..5a8f7dd 100644 --- a/basics/files.md +++ b/basics/files.md @@ -365,9 +365,10 @@ else: *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/getting-started.md b/basics/getting-started.md index 720af5a..9f00625 100644 --- a/basics/getting-started.md +++ b/basics/getting-started.md @@ -212,9 +212,10 @@ enough when you need to calculate something. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/handy-stuff-strings.md b/basics/handy-stuff-strings.md index 03f2208..98d5cc4 100644 --- a/basics/handy-stuff-strings.md +++ b/basics/handy-stuff-strings.md @@ -241,82 +241,17 @@ Instead it's recommended to use string formatting. It means putting other things in the middle of a string. Python has multiple ways to format strings. One is not necessarily -better than others, they are just different. Here's a few ways to solve -our problem: +better than others; they each have their own advantages and disadvantages. +In this tutorial, we will focus on f-strings, which is the most common and usually the easiest way. -- `.format()`-formatting, also known as new-style formatting. This - formatting style has a lot of features, but it's a little bit more - typing than `%s`-formatting. - - ```python - >>> "Hello {}.".format(name) - 'Hello Akuli.' - >>> "My name is {} and I'm on the {} channel on {}.".format(name, channel, network) - "My name is Akuli and I'm on the ##learnpython channel on freenode." - >>> - ``` - -- `%s`-formatting, also known as old-style formatting. This has less - features than `.format()`-formatting, but `'Hello %s.' % name` is - shorter and faster to type than `'Hello {}.'.format(name)`. I like - to use `%s` formatting for simple things and `.format` when I need - more powerful features. - - ```python - >>> "Hello %s." % name - 'Hello Akuli.' - >>> "My name is %s and I'm on the %s channel on %s." % (name, channel, network) - "My name is Akuli and I'm on the ##learnpython channel on freenode." - >>> - ``` - - In the second example we had `(name, channel, network)` on the right - side of the `%` sign. It was a tuple, and we'll talk more about them - [later](lists-and-tuples.md#tuples). - - If we have a variable that may be a tuple we need to wrap it in another - tuple when formatting: - - ```python - >>> thestuff = (1, 2, 3) - >>> "we have %s" % thestuff - Traceback (most recent call last): - File "", line 1, in - TypeError: not all arguments converted during string formatting - >>> "we have %s and %s" % ("hello", thestuff) - 'we have hello and (1, 2, 3)' - >>> "we have %s" % (thestuff,) - 'we have (1, 2, 3)' - >>> - ``` - - Here `(thestuff,)` was a tuple that contained nothing but `thestuff`. - -- f-strings are even less typing, but new in Python 3.6. **Use this only if - you know that nobody will need to run your code on Python versions older - than 3.6.** Here the f is short for "format", and the content of the - string is same as it would be with `.format()` but we can use variables - directly. - - ```python - >>> f"My name is {name} and I'm on the {channel} channel on {network}." - "My name is Akuli and I'm on the ##learnpython channel on freenode." - >>> - ``` - -All of these formatting styles have many other features also: +`f` in f-strings stands for "format", f-strings are string literals that have an `f` at the beginning and curly braces containing expressions that will be replaced with their values at runtime. To create f-strings, you have to add an `f` or an `F` before the opening quotes of a string. ```python ->>> 'Three zeros and number one: {:04d}'.format(1) -'Three zeros and number one: 0001' ->>> 'Three zeros and number one: %04d' % 1 -'Three zeros and number one: 0001' +>>> f"My name is {name} and I'm on the {channel} channel on {network}." +"My name is Akuli and I'm on the ##learnpython channel on freenode." >>> ``` -If you need to know more about formatting I recommend reading -[this](https://pyformat.info/). - ## Other things We can use `in` and `not in` to check if a string contains another @@ -392,7 +327,7 @@ ValueError: could not convert string to float: 'hello' - Python has many string methods. Use [the documentation](https://docs.python.org/3/library/stdtypes.html#string-methods) - or `help(str)` when you don't rememeber something about them. + or `help(str)` when you don't remember something about them. - String formatting means adding other things to the middle of a string. There are multiple ways to do this in Python. You should know how to use at least one of these ways. @@ -431,9 +366,10 @@ The answers are [here](answers.md#handy-stuff-strings). *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/if.md b/basics/if.md index 9247ed6..71655f2 100644 --- a/basics/if.md +++ b/basics/if.md @@ -317,9 +317,10 @@ The answers are [here](answers.md#if-else-and-elif). *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/installing-python.md b/basics/installing-python.md index 755e509..249cc4b 100644 --- a/basics/installing-python.md +++ b/basics/installing-python.md @@ -78,9 +78,10 @@ Now you should have Python installed, and you should be able run it. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/larger-program.md b/basics/larger-program.md index f8f9bfa..4cd0cda 100644 --- a/basics/larger-program.md +++ b/basics/larger-program.md @@ -82,7 +82,7 @@ def ask_questions(answers): print("Correct!") correct.append(question) else: - print("Wrong! The correct answer is %s." % answer) + print(f"Wrong! The correct answer is {answer}.") wrong.append(question) return (correct, wrong) @@ -181,11 +181,11 @@ def ask_questions(answers): wrong = [] for question, answer in answers.items(): - if input('%s = ' % question).strip() == answer: + if input(f'{question} = ').strip() == answer: print("Correct!") correct.append(question) else: - print("Wrong! The correct answer is %s." % answer) + print(f"Wrong! The correct answer is {answer}.") wrong.append(question) return (correct, wrong) @@ -228,9 +228,10 @@ something else when it's imported. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/lists-and-tuples.md b/basics/lists-and-tuples.md index a231de9..379d019 100644 --- a/basics/lists-and-tuples.md +++ b/basics/lists-and-tuples.md @@ -375,9 +375,10 @@ The answers are [here](answers.md#lists-and-tuples). *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/loops.md b/basics/loops.md index 4e69c60..7f693e1 100644 --- a/basics/loops.md +++ b/basics/loops.md @@ -416,7 +416,7 @@ while True: print("I don't know anybody yet.") else: for name in namelist: - print("I know %s!" % name) + print(f"I know {name}!") else: print("I don't understand :(") @@ -493,13 +493,14 @@ The answers are [here](answers.md#loops). *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See [LICENSE](../LICENSE). -[Previous](lists-and-tuples.md) | [Next](trey-hunner-zip-and-enumerate.md) | +[Previous](lists-and-tuples.md) | [Next](zip-and-enumerate.md) | [List of contents](../README.md#basics) diff --git a/basics/modules.md b/basics/modules.md index b8dccbf..59159cd 100644 --- a/basics/modules.md +++ b/basics/modules.md @@ -369,8 +369,8 @@ for thing in things: ``` Measure how long it takes for the user to answer a question. -The `%.2f` rounds to 2 decimals, and you can find more formatting -tricks [here](https://pyformat.info/). +The `{:.2f}` rounds to 2 decimals, and you can find more formatting +tricks [here](https://docs.python.org/3/tutorial/inputoutput.html#formatted-string-literals). ```python import time @@ -381,7 +381,7 @@ end = time.time() difference = end - start if answer == '3': - print("Correct! That took %.2f seconds." % difference) + print(f"Correct! That took {difference:.2f} seconds.") else: print("That's not correct...") ``` @@ -410,7 +410,7 @@ Check what a path points to. import os import sys -print("You are currently in %s." % os.getcwd()) +print(f"You are currently in {os.getcwd()}.") while True: path = input("A path, or nothing at all to quit: ") @@ -488,9 +488,10 @@ section at the bottom. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/the-way-of-the-program.md b/basics/the-way-of-the-program.md index ebb44bc..7def31a 100644 --- a/basics/the-way-of-the-program.md +++ b/basics/the-way-of-the-program.md @@ -38,9 +38,10 @@ learned everything. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/trey-hunner-zip-and-enumerate.md b/basics/trey-hunner-zip-and-enumerate.md deleted file mode 100644 index 3a211de..0000000 --- a/basics/trey-hunner-zip-and-enumerate.md +++ /dev/null @@ -1,147 +0,0 @@ -# Trey Hunner: zip and enumerate - -Now we know how [for loops](loops.md#for-loops) work in Python. But -for loops aren't limited to printing each item in a list, they can -do a lot more. - -To be able to understand for loop tricks we need to first know -assigning values to multiple variables at once. It works like this: - -```python ->>> a, b = 1, 2 ->>> a -1 ->>> b -2 ->>> -``` - -We can use `()` and `[]` around these values however we want and -everything will still work the same way. `[]` creates a list, and -`()` creates a tuple. - -```python ->>> [a, b] = (1, 2) ->>> a -1 ->>> b -2 ->>> -``` - -We can also have `[]` or `()` on one side but not on the other -side. - -```python ->>> (a, b) = 1, 2 ->>> a -1 ->>> b -2 ->>> -``` - -Python created a tuple automatically. - -```python ->>> 1, 2 -(1, 2) ->>> -``` - -If we're for looping over a list with pairs of values in it we -could do this: - -```python ->>> items = [('a', 1), ('b', 2), ('c', 3)] ->>> for pair in items: -... a, b = pair -... print(a, b) -... -a 1 -b 2 -c 3 ->>> -``` - -Or we can tell the for loop to unpack it for us. - -```python ->>> for a, b in items: -... print(a, b) -... -a 1 -b 2 -c 3 ->>> -``` - -Now you're ready to read [this awesome looping -tutorial](http://treyhunner.com/2016/04/how-to-loop-with-indexes-in-python/). -Read it now, then come back here and do the exercises. - -## Exercises - -1. Create a program that works like this. Here I entered everything - after the `>` prompt that the program displayed. - - ``` - Enter something, and press Enter without typing anything when you're done. - >hello there - >this is a test - >it seems to work - > - Line 1 is: hello there - Line 2 is: this is a test - Line 3 is: it seems to work - ``` - -2. Create a program that prints all letters from A to Z and a to z - next to each other: - - ``` - A a - B b - C c - ... - X x - Y y - Z z - ``` - - Start your program like this: - - ```python - uppercase = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' - lowercase = 'abcdefghijklmnopqrstuvwxyz' - ``` - - **Hint:** how do strings behave with `zip`? Try it out on the - `>>>` prompt and see. - -3. Can you make it print the indexes also? - - ``` - 1 A a - 2 B b - 3 C c - ... - 24 X x - 25 Y y - 26 Z z - ``` - -The answers are [here](answers.md). - -*** - -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a -star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). - -You may use this tutorial freely at your own risk. See -[LICENSE](../LICENSE). - -[Previous](loops.md) | [Next](dicts.md) | -[List of contents](../README.md#basics) diff --git a/basics/using-functions.md b/basics/using-functions.md index 123910a..c8255ff 100644 --- a/basics/using-functions.md +++ b/basics/using-functions.md @@ -228,9 +228,10 @@ should work normally. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/variables.md b/basics/variables.md index a272424..f1a8030 100644 --- a/basics/variables.md +++ b/basics/variables.md @@ -301,9 +301,10 @@ what you are doing. We'll learn more about it later. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/what-is-programming.md b/basics/what-is-programming.md index 40e37a6..269ce3f 100644 --- a/basics/what-is-programming.md +++ b/basics/what-is-programming.md @@ -157,9 +157,10 @@ if you don't understand the code. *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/what-is-true.md b/basics/what-is-true.md index 495aea6..a344239 100644 --- a/basics/what-is-true.md +++ b/basics/what-is-true.md @@ -213,9 +213,10 @@ if value is None: ... # best *** -If you have trouble with this tutorial please [tell me about -it](../contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/basics/zip-and-enumerate.md b/basics/zip-and-enumerate.md new file mode 100644 index 0000000..f1332d3 --- /dev/null +++ b/basics/zip-and-enumerate.md @@ -0,0 +1,248 @@ +# zip and enumerate + +Now we know how [for loops](loops.md#for-loops) work in Python. But +for loops aren't limited to printing each item in a list, they can +do a lot more. + +To be able to understand for loop tricks we need to first know +assigning values to multiple variables at once. It works like this: + +```python +>>> a, b = 1, 2 +>>> a +1 +>>> b +2 +>>> +``` + +We can use `()` and `[]` around these values however we want and +everything will still work the same way. `[]` creates a list, and +`()` creates a tuple. + +```python +>>> [a, b] = (1, 2) +>>> a +1 +>>> b +2 +>>> +``` + +We can also have `[]` or `()` on one side but not on the other +side. + +```python +>>> (a, b) = 1, 2 +>>> a +1 +>>> b +2 +>>> +``` + +Python created a tuple automatically. + +```python +>>> 1, 2 +(1, 2) +>>> +``` + +If we're for looping over a list with pairs of values in it we +could do this: + +```python +>>> items = [('a', 1), ('b', 2), ('c', 3)] +>>> for pair in items: +... a, b = pair +... print(a, b) +... +a 1 +b 2 +c 3 +>>> +``` + +Or we can tell the for loop to unpack it for us. + +```python +>>> for a, b in items: +... print(a, b) +... +a 1 +b 2 +c 3 +>>> +``` + +This feature is often used with Python's built-in `zip()` and `enumerate()` functions. + + +## zip + +What comes to your mind when you hear the word `zip`? A mechanism extensively used to tie two parts of something, e.g. shirt or jacket. Python's `zip()` functions does pretty much the same, it helps us tie corresponding items together. + +```python +>>> users = ["Tushar", "Aman", "Anurag", "Sohit"] +>>> uids = ["usr122", "usr123", "usr124", "usr125"] +>>> user_details = zip(uids, users) +>>> print(list(user_details)) +[('usr122', 'Tushar'), ('usr123', 'Aman'), ('usr124', 'Anurag'), ('usr125', 'Sohit')] +>>> +``` + +Note that `print(user_details)` doesn't work as expected: + +``` +>>> print(user_details) + +>>> +``` + +This is because `zip()` is an iterator, i.e. lazy: it gives the items as needed, instead of calculating them and storing them into memory all at once like a list. So the zip object cannot show its elements before the elements are used, because it hasn't computed them yet. + +```python +>>> users = ["Tushar", "Aman", "Anurag", "Sohit"] +>>> uids = ["usr122", "usr123", "usr124", "usr125"] +>>> user_details = zip(uids, users) +``` + +If the lists are of different lengths, some items from the end of the longer list will be ignored. +```python +>>> users = ["Tushar", "Aman", "Anurag"] +>>> emails = ["tushar@example.com", "aman@example.com", "anurag@example.com", "sohit@example.com"] +>>> users_contact = zip(users, emails) +>>> print(list(users_contact)) +[('Tushar', 'tushar@example.com'), ('Aman', 'aman@example.com'), ('Anurag', 'anurag@example.com')] +>>> +``` + + +Here the shortest list is `users`, with length 3, so `zip(users, emails)` only takes the first 3 emails. +We do not recommend calling `zip()` with lists of different lengths, because ignoring items is usually not what you intended to do. + +### Using zip in a `for` loop + +It is very common to `for` loop over a `zip()`, and unpack the returned tuples in the `for` loop. +This is why we introduced unpacking in the beginning of this page. +When used this way, there's no need to convert the result of `zip(...)` to a list. + +```python +>>> roll_nums = [20, 25, 28] +>>> students = ["Joe", "Max", "Michel"] +>>> for roll_num, student in zip(roll_nums, students): +... print(f"Roll number of {student} is {roll_num}") +... +Roll number of Joe is 20 +Roll number of Max is 25 +Roll number of Michel is 28 +>>> +``` + +## enumerate + +`enumerate()` is an amazing Built-in function offered by python. When used, gives us the index and the item combined. + +```python +>>> even_nums = [2, 4, 6, 8, 10, 12] +>>> for index, item in enumerate(even_nums): +... print(f"Index of {item} is {index}") +... +Index of 2 is 0 +Index of 4 is 1 +Index of 6 is 2 +Index of 8 is 3 +Index of 10 is 4 +Index of 12 is 5 +>>> +``` + +It is also possible (but more difficult) to do this without `enumerate()`: + +```python +>>> even_nums = [2, 4, 6, 8, 10, 12] +>>> for index in range(0, len(even_nums)): +... print(f"Index of {even_nums[index]} is {index}") +... +Index of 2 is 0 +Index of 4 is 1 +Index of 6 is 2 +Index of 8 is 3 +Index of 10 is 4 +Index of 12 is 5 +>>> +``` + +Here: +* `range(0, len(even_nums))` gives 0,1,2,3,4,5, with the list length 6 excluded. These are the indexes of our list of length 6. +* `even_nums[index]` prints each element of `even_nums`, because `index` comes from the range of all indexes into that list. + +Because this is complicated to think about and easy to get wrong, it is better to use `enumerate()`. + +## Exercises + +1. Create a program that works like this. Here I entered everything + after the `>` prompt that the program displayed. + + ``` + Enter something, and press Enter without typing anything when you're done. + >hello there + >this is a test + >it seems to work + > + Line 1 is: hello there + Line 2 is: this is a test + Line 3 is: it seems to work + ``` + +2. Create a program that prints all letters from A to Z and a to z + next to each other: + + ``` + A a + B b + C c + ... + X x + Y y + Z z + ``` + + Start your program like this: + + ```python + uppercase = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' + lowercase = 'abcdefghijklmnopqrstuvwxyz' + ``` + + **Hint:** how do strings behave with `zip`? Try it out on the + `>>>` prompt and see. + +3. Can you make it print the indexes also? + + ``` + 1 A a + 2 B b + 3 C c + ... + 24 X x + 25 Y y + 26 Z z + ``` + +The answers are [here](answers.md). + +*** + +If you have trouble with this tutorial, please +[tell me about it](../contact-me.md) and I'll make this tutorial better, +or [ask for help online](../getting-help.md). +If you like this tutorial, please [give it a +star](../README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). + +You may use this tutorial freely at your own risk. See +[LICENSE](../LICENSE). + +[Previous](loops.md) | [Next](dicts.md) | +[List of contents](../README.md#basics) diff --git a/classes.md b/classes.md index 42ecdc6..0306c61 100644 --- a/classes.md +++ b/classes.md @@ -2,9 +2,10 @@ This file has been moved [here](basics/classes.md). *** -If you have trouble with this tutorial please [tell me about -it](./contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](./contact-me.md) and I'll make this tutorial better, +or [ask for help online](./getting-help.md). +If you like this tutorial, please [give it a star](./README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/common.py b/common.py index 51c22eb..7180739 100644 --- a/common.py +++ b/common.py @@ -122,16 +122,6 @@ def askyesno(question, default=True): print("Please type y, n or nothing at all.") -def slashfix(path): - """Replace / with os.sep.""" - return path.replace('/', os.sep) - - -def slashfix_open(file, mode): - """An easy way to use slashfix() and open() together.""" - return open(slashfix(file), mode) - - @contextlib.contextmanager def backup(filename): """A context manager that backs up a file.""" diff --git a/contact-me.md b/contact-me.md index 0f5aeea..eff6885 100644 --- a/contact-me.md +++ b/contact-me.md @@ -13,14 +13,15 @@ it, there are a few ways to contact me: - Tell me on IRC. - I'm usually on ##learnpython and ##python-friendly on freenode. See + I'm regularly on ##learnpython on libera. See [Getting help](getting-help.md) for instructions to getting there. *** -If you have trouble with this tutorial please [tell me about -it](./contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](./contact-me.md) and I'll make this tutorial better, +or [ask for help online](./getting-help.md). +If you like this tutorial, please [give it a star](./README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/getting-help.md b/getting-help.md index c621433..e56e7a2 100644 --- a/getting-help.md +++ b/getting-help.md @@ -3,59 +3,63 @@ When you have a problem with Python, you're not alone! There are many places to ask for help in. +Regardless of where you ask for help, please: +- Don't ask "does someone know ...". Just ask about your problem right away. +- Make your question short. +- Include everything that other people will need to answer your question. + For example, if you are getting an error, include your code and the error message. + + ## IRC -IRC is the oldest chatting service I know, but as of 2018, it's still -in use, and a great way to get help in Python. You don't need to -register anywhere, just click one of the links below and you're good to -go. - -- [##learnpython](https://kiwiirc.com/client/chat.freenode.net/##learnpython) and - [##python-friendly](https://kiwiirc.com/client/chat.freenode.net/##python-friendly) - are beginner-friendly Python support channels. In my experience, - people here tend to understand beginners' problems better, so you - probably want to go to one of these. -- [#python](https://kiwiirc.com/client/chat.freenode.net/#python) is - the official Python channel. If you have questions about advanced - topics or you need help quickly, go there. However, this channel - requires - [registering on freenode](http://www.wikihow.com/Register-a-Nickname-on-Freenode). - -Make your question short. If you want to post a code example that is -more than two lines long, post it [here](http://dpaste.com/) first. +IRC is the oldest chatting service I know, but as of 2022, it's still +in use, and a good way to get help in Python. +An advantage with IRC is that you don't need to create an account to use it. + +To get started, go to https://web.libera.chat/ and type `##learnpython` or `#python` for the channel name. + +- `##learnpython` is a channel where I am regularly, but there's usually only about 20 people there, + so it could be that nobody answers your question, depending on what time it is. + I'm on `##learnpython` at about 7PM to 10PM UTC. + If you see `Akuli` in the user list, that's me :) +- `#python` is an active channel that I don't use much, but someone will likely answer your question pretty quickly. + +If you want to post more than 3 lines of code, +put it to [dpaste.com](https://dpaste.com/) first. Just copy-paste your code to the big text area and click the "Paste it" button, and then post a link to your paste on IRC. +Otherwise every line of your code will appear as a separate message on IRC, +so if your code is 15 lines, just pasting it in will produce 15 different messages. +This would be annoying. + + +## Discord -Do this: +If you have a discord account, you can click the "Explore Public Servers" button at bottom left. - i'm trying to check if this variable equals one but i keep - getting an error http://dpaste.com/yourpaste +![Discord's explore public servers button](images/discord-explore.png) -Don't do this: +You can then search for e.g. Python, and you should find many servers to choose from. +I am currently @Akuli on a server called "The Programmer's Hangout". - HEEEEELP MEEEEEEEEEEEEEEE!!! - File "hello.py", line 3 - if a = b: - ^ - SyntaxError: invalid syntax ## Websites to ask help on Personally, I've never asked a question on any of these sites. Getting help on IRC is much faster. -- [stackoverflow](http://stackoverflow.com/) is a question/answer site +- [stackoverflow](https://stackoverflow.com/) is a question/answer site for programmers. Search for your question first, maybe someone has already asked that and it has been answered. -- At the time of writing this, - [the learnpython subreddit](https://www.reddit.com/r/learnpython/) +- [The learnpython subreddit](https://www.reddit.com/r/learnpython/) is another good place to ask Python questions on. *** -If you have trouble with this tutorial please [tell me about -it](./contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](./contact-me.md) and I'll make this tutorial better, +or [ask for help online](./getting-help.md). +If you like this tutorial, please [give it a star](./README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See diff --git a/images/discord-explore.png b/images/discord-explore.png new file mode 100644 index 0000000..1162495 Binary files /dev/null and b/images/discord-explore.png differ diff --git a/linkcheck.py b/linkcheck.py index 35ced72..2dcd4c5 100755 --- a/linkcheck.py +++ b/linkcheck.py @@ -59,18 +59,17 @@ def check(this_file, target, title, titledict): path = posixpath.join(posixpath.dirname(this_file), target) path = posixpath.normpath(path) - real_path = common.slashfix(path) - if not os.path.exists(real_path): + if not os.path.exists(path): return "doesn't exist" if target.endswith('/'): # A directory. - if not os.path.isdir(real_path): + if not os.path.isdir(path): return "not a directory" else: # A file. - if not os.path.isfile(real_path): + if not os.path.isfile(path): return "not a file" if title is not None and title not in titledict[path]: @@ -82,7 +81,7 @@ def find_titles(filename): """Read titles of a markdown file and return a list of them.""" result = [] - with common.slashfix_open(filename, 'r') as f: + with open(filename, 'r') as f: for line in f: if line.startswith('```'): # it's a code block, let's skip to the end of it to @@ -103,7 +102,7 @@ def find_links(this_file): """ result = [] - with common.slashfix_open(this_file, 'r') as f: + with open(this_file, 'r') as f: for match, lineno in common.find_links(f): target = match.group(2) if '#' in target: @@ -122,7 +121,7 @@ def find_links(this_file): def get_line(filename, lineno): """Return the lineno'th line of a file.""" - with common.slashfix_open(filename, 'r') as f: + with open(filename, 'r') as f: for lineno2, line in enumerate(f, start=1): if lineno == lineno2: return line diff --git a/make-html.py b/make-html.py index 4ae6d5a..b40ec3a 100755 --- a/make-html.py +++ b/make-html.py @@ -30,25 +30,26 @@ import argparse import os +import platform import posixpath import shutil import sys import textwrap import webbrowser +if platform.system() == 'Windows': + python = 'py' +else: + python = 'python3' + try: import mistune except ImportError: - import platform - if platform.system() == 'Windows': - python = 'py' - else: - python = 'python3' print("mistune isn't installed.", file=sys.stderr) print("You can install it by running this command on a terminal or ") print("command prompt:") print() - print(" %s -m pip install --user mistune" % python) + print(" %s -m pip install mistune" % python) sys.exit(1) try: @@ -91,12 +92,11 @@ class TutorialStyle(pygments.style.Style): """ -def mkdir_slashfix_open(filename, mode): - """Like common.slashfix_open(), but make directories as needed.""" - real_filename = common.slashfix(filename) - directory = os.path.dirname(real_filename) +def mkdir_and_open(filename, mode): + """Like open(), but make directories as needed.""" + directory = os.path.dirname(filename) os.makedirs(directory, exist_ok=True) - return open(real_filename, mode) + return open(filename, mode) def fix_filename(filename): @@ -112,7 +112,7 @@ def fix_filename(filename): return filename -class TutorialRenderer(mistune.Renderer): +class TutorialRenderer(mistune.HTMLRenderer): def __init__(self, pygments_style): super().__init__() @@ -226,8 +226,7 @@ def main(): if pygments is None: print("Pygments isn't installed. You can install it like this:") print() - print(">>> import pip") - print(">>> pip.main(['install', '--user', 'pygments'])") + print(" %s -m pip install pygments" % python) print() print("You can also continue without Pygments, but the code examples") print("will not be colored.") @@ -252,7 +251,7 @@ def main(): htmlfile = posixpath.join(args.outdir, fixed_file) print(' %-30.30s --> %-30.30s' % (markdownfile, htmlfile), end='\r') - with common.slashfix_open(markdownfile, 'r') as f: + with open(markdownfile, 'r') as f: markdown = f.read() renderer = TutorialRenderer(args.pygments_style) body = mistune.markdown(markdown, renderer=renderer) @@ -264,7 +263,7 @@ def main(): body=body, stylefile=stylefile, ) - with mkdir_slashfix_open(htmlfile, 'w') as f: + with mkdir_and_open(htmlfile, 'w') as f: print(html, file=f) print() diff --git a/update-ends.py b/update-ends.py index 820ef6a..9b2d1ef 100755 --- a/update-ends.py +++ b/update-ends.py @@ -35,9 +35,10 @@ END_TEMPLATE = """\ -If you have trouble with this tutorial please [tell me about -it]({toplevel}/contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it]({toplevel}/contact-me.md) and I'll make this tutorial better, +or [ask for help online]({toplevel}/getting-help.md). +If you like this tutorial, please [give it a star]({toplevel}/README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See @@ -85,7 +86,7 @@ def update_end(filename, end): separator. """ end = '\n***\n\n' + end - with common.slashfix_open(filename, 'r') as f: + with open(filename, 'r') as f: content = f.read() if content.endswith(end): # No need to do anything. @@ -96,11 +97,11 @@ def update_end(filename, end): # We need to remove the old ending first. print(" Removing old end:", filename) where = content.index('\n***\n') - with common.slashfix_open(filename, 'w') as f: + with open(filename, 'w') as f: f.write(content[:where]) print(" Adding end:", filename) - with common.slashfix_open(filename, 'a') as f: + with open(filename, 'a') as f: f.write(end) diff --git a/what-next.md b/what-next.md index bd2de84..8437d95 100644 --- a/what-next.md +++ b/what-next.md @@ -31,9 +31,10 @@ is a way to create generators *** -If you have trouble with this tutorial please [tell me about -it](./contact-me.md) and I'll make this tutorial better. If you -like this tutorial, please [give it a +If you have trouble with this tutorial, please +[tell me about it](./contact-me.md) and I'll make this tutorial better, +or [ask for help online](./getting-help.md). +If you like this tutorial, please [give it a star](./README.md#how-can-i-thank-you-for-writing-and-sharing-this-tutorial). You may use this tutorial freely at your own risk. See