The Curious Engineer

All blogs / Python

LernerPython

lernerpython.com

Practical Python, Pandas, Git, and PostgreSQL articles from Reuven Lerner: short, hands-on explanations drawn from 30+ years of teaching developers.

PythonDatabasesEngineering blogs

Posts
536 from 27 Oct 2013 to 30 Oct 2026
Posting
about daily (284 in the last year)
Kind
company blog
Feed
https://lernerpython.com/feed/

2026 281

  1. Pandas MultiIndex: What a two-level index looks like
  2. Pandas xs: Keep the dropped level with drop_level=False
  3. Pandas xs: Using the `level` argument with an int or a name
  4. Pandas MultiIndex: Select rows by the outer level with loc
  5. Pandas offset aliases for resample: ME, MS, and other codes
  6. Pandas DatetimeIndex slicing: Fix KeyError with sort_index
  7. Pandas date range selection: Slicing a datetime index with .loc
  8. Pandas Grouper NaNs: Why outlier dates create empty groups
  9. Pandas Grouper: Group datetime columns by custom time periods
  10. Pandas groupby on datetime parts with the dt accessor
  11. Pandas groupby: Aggregating multiple columns with multiple functions
  12. Pandas groupby: Multiple columns and multiple aggregation methods
  13. Pandas groupby: Get a data frame instead of a series
  14. Pandas groupby with two columns: Reshape results with unstack
  15. Pandas groupby with sort=False: Keep groups in order of appearance
  16. Pandas groupby basics: Aggregating a numeric column by category
  17. Pandas dropna with thresh: Drop only rows with too many NaN values
  18. Pandas dropna: The best way to remove NaN values from a series
  19. New on the LernerPython practice system: A visual debugger
  20. PyArrow dtypes in pandas: Nullable integers with pd.NA
  21. Pandas nullable integers: Keeping ints with Int64 and pd.NA
  22. Get Python help, one on one: my coaching sessions
  23. NaN in Pandas: Why you need np.nan, not pd.NaN
  24. np.nan in Pandas: Why missing values break comparisons
  25. Python callables: Any object that defines __call__
  26. Python += calls __add__ and rebinds to a new object
  27. Python in operator: How __contains__ speeds up membership tests
  28. Newsprint: Turning e-mail newsletters into a personal PDF
  29. Python | operator: Bitwise or and dict merging with __or__
  30. Python `__mod__`: Modulo for numbers, interpolation for str
  31. Python operator overloading: The arithmetic magic methods
  32. Claude Code always produces something. That’s the hard part.
  33. Python’s __radd__: How reflected operators handle 5 + x
  34. Python `__add__`: Return a new instance, not an int
  35. Python operator overloading: Implementing __add__ for +
  36. Python operator overloading: Why x + y and y + x give different errors
  37. Mutable default arguments in Python: why `__defaults__` bites
  38. Python generator frames: Inspecting locals with gi_frame
  39. MIT just called for an educational revolution
  40. AI seminars — just one of the big changes at LernerPython
  41. PyArrow dtypes in Pandas aren’t always faster than NumPy
  42. PyArrow strings in pandas: Faster and smaller than object dtype
  43. PyArrow dtypes in pandas: Reading CSVs with dtype_backend
  44. Pandas 3 string dtype: PyArrow strings cut memory use
  45. PyArrow dtypes in Pandas 3: Missing values without float conversion
  46. Pandas missing values: Why assigning pd.NA gives you float64
  47. Pandas int8 overflow: Why small dtypes wrap around silently
  48. Pandas read_csv dtype: Setting column types to save memory
  49. Changing a Pandas column dtype: Use astype, not assignment
  50. Pandas dtypes: Checking column types with dtype and value_counts
  51. Pandas data frame preview: df.head and df.sample
  52. Free real-world Pandas exercises, with solutions
  53. Pandas read_csv reads zipped CSV files without unzipping
  54. Excel sheet names in Pandas: Listing them with pd.ExcelFile
  55. Pandas isin vs | for filtering: which is faster
  56. Pandas isin: Filtering rows that match multiple values
  57. Pandas OR conditions: Filtering rows with | and parentheses
  58. Pandas loc filter order: Put the most selective filter first
  59. Filtering rows in Pandas with .loc and pd.col
  60. Python list memory: Why sys.getsizeof ignores the elements
  61. Redirecting stderr in Python: Using contextlib.redirect_stderr
  62. redirect_stdout in Python: Sending print output to a file
  63. Python stderr: Printing with sys.stderr and the file kwarg
  64. Python print to a file: Using the file keyword argument
  65. Redirecting sys.stdout: Assigning print output to a file
  66. Python frozen modules: Why they have no __file__ attribute
  67. importlib.reload: Reimporting a Python module during development
  68. Python import: How a module name becomes a file on sys.path
  69. PYTHONPATH: A scalable alternative to sys.path.insert
  70. sys.path supports zipfiles: Importing modules from an archive
  71. sys.path: How Python finds the modules you import
  72. sys.modules: How Python caches already-loaded modules
  73. Importing sys in Python: What the import statement really does
  74. Python version at runtime: sys.version vs sys.version_info
  75. Python Enum auto(): Generating unique values automatically
  76. Python Enum iteration: Looping over __members__.items()
  77. Python Enum duplicate values: Preventing aliases with @unique
  78. Python Enum sorting: Use IntEnum for comparable members
  79. Python enums: Symbolic constants that print nicely but don’t sort
  80. Python constants: Blocking reassignment with Final and mypy
  81. Immutable vs. constant in Python: Why constants aren’t enforced
  82. Python dict.items(): Set operations on key-value pairs
  83. Python dict.keys(): Using set operators on dictionary keys
  84. dict.pop vs dict.popitem: Removing items from a Python dictionary
  85. Python dict.pop: Removing keys with a default fallback
  86. Merging Python dictionaries with |: Right side wins conflicts
  87. Modifying a Python dict during iteration raises RuntimeError
  88. Python dict iteration: Using items to get keys and values
  89. Python dictionary equality: Insertion order doesn’t matter
  90. Python dict of lists: Using defaultdict from collections
  91. Python dicts of lists: Grouping values with setdefault
  92. Python dict.setdefault: Assign only when the key is missing
  93. Python dictionaries: Avoiding KeyError with dict.get
  94. Python dict key lookup: Use in instead of d.keys()
  95. Python dict creation speed: Literal vs dict vs comprehension
  96. Pandas .loc slicing on a non-unique index: sort_index() first
  97. Pandas .loc: Selecting rows, columns, and slices by label
  98. Pandas .loc filtering: Replacing lambda with pd.col
  99. Pandas row filtering: Using df.loc with a lambda expression
  100. Filtering a Pandas series with loc and lambda: Three benefits
  101. Pandas Series filtering: Use loc with lambda to chain filters
  102. Pandas Series filtering: Chaining loc for multiple conditions
  103. Pandas Series filtering: Split long conditions across lines
  104. Pandas boolean filtering: Wrap each condition in parentheses
  105. Pandas boolean indexing: Selecting series items with a mask
  106. New: In-browser Python/Pandas/Git exercises, with AI support
  107. Pandas Series .loc: Selecting with labels and booleans
  108. Pandas Series broadcasting: Arithmetic and comparisons with scalars
  109. Pandas Series selection speed: iloc[:2] beats loc and head
  110. .loc vs .iloc in Pandas: Convenience versus speed
  111. Pandas iloc vs loc: Selecting series values by position
  112. Pandas .loc with a list returns a series, not a scalar
  113. Pandas Series duplicate index labels: When .loc returns a Series
  114. Pandas Series indexing: Why .loc beats [] for retrieval
  115. Pandas set_axis: Replacing a Series index without mutating it
  116. Pandas Series index: Change it by assigning to s.index
  117. Pandas Series index: Setting labels instead of RangeIndex
  118. isinstance vs type(): The safer way to check Python types
  119. Python inheritance: When to use it and when to prefer composition
  120. Python metaclasses: How they work and when to use a decorator instead
  121. Python metaclasses: How type.__new__ and type.__init__ create classes
  122. object and type in Python: The circular class hierarchy
  123. Python MRO errors: Why child classes must precede parents
  124. super() without arguments: How Python finds self and the MRO
  125. Python cooperative inheritance: How super() walks the MRO
  126. Python multiple inheritance: How super() follows the MRO
  127. Python multiple inheritance: Why every class needs super()
  128. Python multiple inheritance: Which __init__ actually runs
  129. Python multiple inheritance: Listing parents with __bases__
  130. Python super() and the MRO: How method lookup climbs the hierarchy
  131. Python inheritance: Skipping super().__init__ loses parent attributes
  132. Python super().__init__: Passing arguments to the parent class
  133. Python super(): Misspelled method names raise AttributeError
  134. Python’s super(): A proxy for calling parent-class methods
  135. Python method overriding: Child methods replace the parent’s
  136. Is Python becoming Pinyin?
  137. Python method resolution order: Inheriting methods from a parent
  138. Python method resolution order: Reading a class’s __mro__
  139. Python class inheritance: Subclassing, __bases__, and isinstance
  140. Python attributes: Instance variables, class variables, and methods
  141. Python attribute lookup: The ICPO rule for finding methods
  142. Python `__bases__`: Every class inherits from object
  143. Composition in Python classes: The has-a relationship
  144. Python composition vs inheritance: The has-a and is-a relationships
  145. Python ternary operator: When to use if-elif-else instead
  146. Python lambda if-else: Use the ternary operator instead
  147. Python’s ternary operator: Conditional expressions in comprehensions
  148. Python `__format__`: Define your own format specification syntax
  149. Python __format__: Detecting an empty format code
  150. Python `__format__`: Custom format codes for your own classes
  151. f-string conversion flags: Using !r to get repr instead of str
  152. Formatting a Python datetime with f-strings and strftime codes
  153. Thousands separators in Python f-strings: Format with commas
  154. Python float to percentage: Format with % in an f-string
  155. Formatting floats in Python f-strings: The .nf specifier
  156. Python f-string format specifiers: Padding and aligning columns
  157. Python f-string format specifiers: Aligning and padding text
  158. Python f-string debugging: Printing expressions with =
  159. Python f-strings are just strings: Use them anywhere
  160. Python f-strings: Embedding expressions inside strings
  161. Pandas datetime rounding: dt.floor, dt.ceil, and dt.round
  162. Pandas dt.normalize: Setting datetime times to midnight
  163. Pandas datetime to Unix time with astype(‘int64’)
  164. Convert Unix timestamps to datetime in Pandas with pd.to_datetime
  165. Pandas to_period: Comparing dates by month, quarter, or year
  166. Pandas to_period: Finding which period contains a datetime
  167. Find leap years in a Pandas datetime series with dt.is_leap_year
  168. Pandas dt.is_month_start: Checking period boundaries in a series
  169. Getting the day of week with `dt.day_of_week` in Pandas
  170. Pandas .dt accessor: Extracting year, hour, and day_of_week
  171. pandas read_csv date parsing: Using the date_format keyword
  172. Take agentic coding to the next level
  173. Pandas parse_dates: Reading CSV date columns as datetimes
  174. pd.to_datetime: Converting a pandas string column to datetimes
  175. Parse ISO date strings in Python with datetime.fromisoformat
  176. Python strptime vs. strftime: Parsing versus formatting dates
  177. Python string to datetime: Parsing dates with strptime
  178. Python datetime formatting: Using strftime for date strings
  179. Timezone-aware datetime objects in Python with zoneinfo
  180. Creating Python datetime objects with datetime.datetime
  181. Python datetime subtraction: Getting a timedelta between two times
  182. Python current date and time: Using datetime.datetime.now()
  183. pandas date_range: Creating a DatetimeIndex with freq
  184. pd.date_range: Evenly spaced Pandas dates with periods
  185. Pandas datetime filtering: Rows before now with pd.Timestamp.now()
  186. Pandas .str.contains: Finding and filtering rows by substring
  187. Python keyword-only parameters: Setting default values
  188. Python keyword-only parameters: Using * and *args in def
  189. Type hints for *args in Python: Annotate the element type
  190. Python *args: Collecting positional arguments into a tuple
  191. Python *args: Accepting any number of positional arguments
  192. Positional vs keyword arguments in Python function calls
  193. Python 3.15 lazy imports: Deferring module load until first use
  194. Python dict keys: Why custom objects work but lists don’t
  195. Python dict keys must be hashable: Why lists don’t work
  196. Do you teach Python? Then check out course-setup
  197. Pandas str.split: Get the first item of a comma-separated column
  198. Pandas str.isdigit: Checking whether strings contain only digits
  199. Pandas string slicing: Extracting substrings with .str.slice
  200. Pandas .str.get: Retrieving characters from string columns
  201. Pandas MultiIndex: Dropping a level with reset_index(drop=True)
  202. Pandas reset_index: Moving multi-index levels back to columns
  203. Pandas reset_index: Turning a data frame’s index into a column
  204. Pandas set_index: Turning columns into a data frame index
  205. Multi-line f-strings in Python: Triple quotes with interpolation
  206. Python multiline strings: \n versus triple quotes
  207. Python string quotes: Handling an apostrophe inside a string
  208. Reading binary files in Python: Use ‘rb’ mode to get bytes
  209. functools.total_ordering: Define two comparison methods, get six
  210. Python `__all__`: Blocking wildcard imports with a fake name
  211. Python __all__: Controlling which names import * exports
  212. Wildcard imports in Python: Why from module import * is a bad idea
  213. Python even/odd checks: Using truthiness instead of == 0
  214. Pandas astype errors=’ignore’: Skip failed dtype conversions
  215. Pandas astype() returns a new Series instead of converting in place
  216. Counting NaN values in a Pandas DataFrame with isna and sum
  217. Counting NaN values in a Pandas series with isna and sum
  218. Python division operators: / returns a float, // rounds down
  219. pandas read_csv header: Which row holds your column names
  220. Pandas pivot vs pivot_table: Handling duplicate values
  221. Pandas join vs merge: Combining data frames by index or column
  222. Pandas agg with a dict: Different aggregations per column
  223. Pandas groupby agg: Applying multiple aggregations at once
  224. Pandas na_values: Treating custom strings as missing data
  225. Python extended unpacking: Using * to assign leftover values
  226. uv version –bump: Increasing your project’s version number
  227. Pandas loc vs iloc slicing: Inclusive vs exclusive endpoints
  228. pandas read_csv: Speed up loading with the PyArrow engine
  229. Pandas category dtype: Reduce string column memory by 90%
  230. Python multi-line comprehensions: Formatting for readability
  231. collections.Counter: Counting values in a Python sequence
  232. OrderedDict vs dict: Why equality checks compare order
  233. Sorting custom Python objects with __lt__ and __eq__
  234. Python str.strip: Removing any characters, not just whitespace
  235. Dispatch tables in Python: Replace if/elif with a dict of functions
  236. Python dict insertion order: What happens when you re-add a key
  237. Python defaultdict: Pass a factory function, not a value
  238. Python positional-only parameters: Fixing **kwargs conflicts
  239. Python str.split and rsplit: Splitting strings with maxsplit
  240. %xmode in IPython: Shortening long Python tracebacks
  241. Pandas columns overlap error: Fixing join with lsuffix and rsuffix
  242. Modifying a Python list while iterating: Only append is safe
  243. Python multiple return values: Returning and unpacking tuples
  244. __setitem__ in Python: Custom logic for square-bracket assignment
  245. Python `__getitem__`: Custom logic behind square brackets
  246. Python __getitem__: Adding bracket notation to your classes
  247. Pandas join: Why you need a one-column DataFrame, not a Series
  248. Pandas currency strings: Strip USD, then astype(float) and sum
  249. Python method calls: Why dict.items needs parentheses
  250. Pandas 3.0 pd.col: Replacing lambda in loc and assign
  251. Python from import doesn’t save memory: The module still loads
  252. What’s new in Pandas 3?
  253. __new__ vs __init__: Why Python constructors rarely need __new__
  254. Pandas Series and DataFrame methods: same names, column-wise results
  255. Reading multi-sheet Excel files in Pandas with sheet_name
  256. uv python pin: Changing the Python version in .python-version
  257. Learn to code with AI — not just write prompts
  258. Unique values from a Python list: Using set() and unpacking
  259. We’re all VCs now: The skills developers need in the AI era
  260. Pandas memory usage: Why you need deep=True for text columns
  261. Build YOUR data dashboard — join my next 8-week HOPPy studio cohort
  262. Pandas read_csv accepts a URL: Loading remote data files
  263. Saving a Pandas plot to a file with get_figure and savefig
  264. Pandas datetime index slicing: sort_index to avoid a KeyError
  265. Sorting a Python dict by value with operator.itemgetter
  266. Python file modes: Use ‘x’ instead of ‘w’ to avoid overwriting
  267. Pandas nlargest: Finding top rows faster than sort_values
  268. Pandas column arguments: Where one name works, a list does too
  269. Python str.join(): Why it’s a string method, not a list method
  270. Pandas sort_values: Sorting a data frame by multiple columns
  271. Pandas select_dtypes: Selecting columns by their dtype
  272. Python line continuation: How parentheses split long lines
  273. Jupyter memory usage: Why del doesn’t free your DataFrame
  274. Python set subset checks with
  275. dict.fromkeys: Why a mutable default value gets shared
  276. Python round and banker’s rounding: Why round(2.5) returns 2
  277. Reverse a string or list in Python with the [::-1] slice
  278. Python sequences: The shared API of str, list, and tuple
  279. Python weekend check: Detecting Saturday and Sunday with weekday()
  280. Python is vs ==: Object identity and value equality
  281. Python numeric literals: Using underscores to group digits

2025 8

  1. Reuven’s 2025 in review
  2. 30 things I’ve learned from 30 years as a Python freelancer
  3. Want to learn uv?
  4. Your personal mentor for Python and Pandas
  5. You’re probably using uv wrong
  6. How to conference
  7. My newest course: HOPPy (Hands-on Projects in Python)
  8. Eleven days on Iceland’s Ring Road

2024 1

  1. Level up your Python skills this August

2023 3

  1. Prepare yourself for a better career, with my new Python learning memberships
  2. I’m banned for life from advertising on Meta. Because I teach Python.
  3. Sharpen your Pandas skills with “Bamboo Weekly”

2022 8

  1. My Week with ChatGPT
  2. Improve your Python skills — at 40% off
  3. Level up your career with PythonDAB — the Python Data Analytics Bootcamp
  4. Upcoming Python/Pandas courses for seasoned coders
  5. Lots of new YouTube videos about Python and Pandas!
  6. How to propose a winning conference talk
  7. Announcing PythonDAB: The course I’ve always wanted to teach
  8. The “why” of object-oriented programming (in Python)

2021 11

  1. Save time — and 30% — with my 25 Python, Git, and data science courses!
  2. Stop fearing Python decorators
  3. Let’s de-confuse Python objects!
  4. Missing my blog posts? Check me out on YouTube!
  5. Level up your Python skills with six new courses
  6. Improve your “pandas” skills with “Pandas Workout”
  7. Python parameters primer
  8. It’s time to learn Python
  9. Write better Python functions!
  10. One year of “Python for non-programmers”
  11. Reminder: Weekly Python Exercise B1 (advanced topics 1) starts on Tuesday!

2020 44

  1. You can, but should you? Combining some of Python’s more esoteric features
  2. This Black Friday, get 40% off all 25 of my Python, Git, and data science courses
  3. Reminder: My “Intro to SQL” course is this Sunday!
  4. Join the data revolution with my “Intro to SQL” course!
  5. Now playing on YouTube: Answers to your Python questions
  6. Last chance: Weekly Python Exercise B3 starts tomorrow!
  7. Improve your Python skills in 15 weeks — with Weekly Python Exercise!
  8. Ask me anything!
  9. What’s the easiest way to boost your career as a software developer? Learn to touch type.
  10. Improve your Python fluency with “Python Workout” — today’s “Deal of the Day”
  11. “Python Workout” is Manning’s “Deal of the Day”!
  12. This Sunday, start writing better Python code
  13. Master object-oriented Python with Weekly Python Exercise — starting September 8th
  14. New course: Testing your Python programs with pytest
  15. TinyMBA — A quick read full of profound strategic ideas
  16. Last chance to get $1400 of Python courses for $25
  17. There’s still time to get amazing Python course deals via Humble Bundle
  18. “Python Workout” is available in print!
  19. Level up your Python skills with a supercharged Humble Bundle!
  20. “Python Workout” is the Manning “Deal of the Day” for June 7
  21. Reminder: Python for non-programmers continues tomorrow!
  22. “Python Workout” is Manning’s Deal of the Day!
  23. Understanding bitwise operations in Python
  24. Today’s lesson in “Python for non-programmers”: Dictionaries
  25. Making sense of generators, coroutines, and “yield from” in Python
  26. Python for non-programmers continues!
  27. Become more fluent with Python functions in just 15 weeks
  28. Reminder: My free, weekly “Python for non-programmers” course continues on Friday, May 1st
  29. Function Dissection Lab: Learn how Python functions work by examining their innards
  30. Working with warnings in Python (Or: When is an exception not an exception?)
  31. Improve your Python: WPE A2 (“Functions for beginners”) starts next week!
  32. Reminder: “Python for non-programmers” continues tomorrow!
  33. It’s Friday — time for another free “Python for non-programmers” session!
  34. Reminder: My free “Python for non-programmers” course continues tomorrow!
  35. Reminder: “Python for non-programmers” continues tomorrow
  36. Announcing: Three new advanced Python courses (and one free course for absolute beginners)
  37. Announcing: Free, weekly “Python for non-programmers” workshop
  38. Last chance to level up your skills with Weekly Python Exercise B1 (advanced topics 1)
  39. “Python Workout” is Manning’s “Deal of the Day”
  40. Want to spend more time coding Python, and less time on Stack Overflow?
  41. Last chance for Weekly Python Exercise A1
  42. Is Weekly Python Exercise for you?
  43. Looking back at 2019, looking forward to 2020
  44. Start the year with better Python fluency

2019 56

  1. Ace Python Interviews — a new, free course to help you get a better job
  2. Last chance for Black Friday pricing
  3. My Black Friday sale is live! Take 50% off any course in Python or data science
  4. Black Friday: All of my Python courses are 50% off!
  5. Podcasts, podcasts, and even more podcasts
  6. Last chance to join Weekly Python Exercise in 2019!
  7. Quick Python tip: “int” strips strings of whitespace
  8. Want to improve your Python fluency? Join Weekly Python Exercise!
  9. Early-bird pricing for Weekly Python Exercise ends tomorrow
  10. Level up your coding skills with Weekly Python Exercise
  11. Looking for Python podcast co-hosts
  12. Last change to join Weekly Python Exercise: Beginner objects
  13. LEGB? Meet ICPO, Python’s search strategy for attributes
  14. Learn and understand Python objects — with Weekly Python Exercise, starting September 17
  15. “Python Workout” is today’s Manning “Deal of the day”
  16. Reminder: Only one day left for early-bird pricing on Weekly Python Exercise A3 (objects for beginners)
  17. Proud to be sponsoring PyCon 2020
  18. Weekly Python Exercise A3 (beginner objects) is open
  19. “Python Workout” is Manning’s deal of the day!
  20. Enjoyed the movie? Now you can also enjoy the (Jupyter note)book!
  21. Weekly Python Exercise is a PyCon Africa 2019 bronze sponsor
  22. It’s my annual birthday sale!
  23. Registration for Weekly Python Exercise closes today!
  24. Announcing: Python standard library, video explainer
  25. Want to level up your Python? Join Weekly Python Exercise, starting July 2nd
  26. Early-bird pricing for Weekly Python Exercise ends today!
  27. Understanding Python assignment
  28. Reminder: Early-bird pricing for Weekly Python Exercise ends tomorrow
  29. Playing with Python strings, lists, and variable names — or, a complex answer to a simple question
  30. “Python Workout” is Manning’s Deal of the Day!
  31. Variables are pronouns: A simple metaphor for Python newbies
  32. Sharpen your Python skills with Weekly Python Exercise
  33. Why do Python lists let you += a tuple, when you can’t + a tuple?
  34. Registration (and early-bird pricing) is open for Weekly Python Exercise
  35. Python dicts and memory usage
  36. Weekly Python Exercise A2 (functions + modules for beginners) closes today
  37. “Python Workout” is Manning’s Deal of the Day!
  38. There’s still time to join Weekly Python Exercise
  39. My interview on the “Talk Python” podcast
  40. Making your Python decorators even better, with functool.wraps
  41. Get code + slides from my “Practical Decorators” talk from Euro Python / PyCon 2019
  42. Announcing: Weekly Python Exercise A2 — functions and modules for Python beginners
  43. Improve your Python skills with my new book: Python Workout
  44. Announcing: My new NumPy course is live!
  45. Python’s “else” clause for loops
  46. Seven ways to improve your team’s Python
  47. Registration for Weekly Python Exercise ends in 24 hours
  48. Understanding Python slices
  49. Want to improve your Python skills? Join the upcoming cohort of Weekly Python Exercise!
  50. The “Train Better” podcast is live!
  51. Answering Python questions from readers
  52. Python’s str.isdigit vs. str.isnumeric
  53. Beyond the “hello, world” of Python’s “print” function
  54. Registration ends today for Weekly Python Exercise
  55. Reminder: Weekly Python Exercise registration ends soon
  56. Announcing a new course: Intro Python — Fundamentals

2018 19

  1. The foreigner’s guide to phone (WeChat + AliPay) payments in China
  2. Announcing: Two Python courses in Tel Aviv
  3. Announcing: Weekly Python Exercise, Newbie Edition
  4. Last chance to save 40% on Python and Git courses
  5. Black Friday sale — improve your Python + Git for 40% off!
  6. Last chance: Weekly Python Exercise registration closes soon
  7. Weekly Python Exercise: Registration closes in two days
  8. Announcing: Weekly Python Exercise, Autumn 2018 cohort
  9. Avoiding Windows backslash problems with Python’s raw strings
  10. A quick intro to the Unix “find” utility
  11. Python parentheses primer
  12. 20% off all books + courses during PyCon
  13. Pycon
  14. Master Python objects (and understand how they work)
  15. Freelancers Show #300 — live!
  16. Announcing my new Python course, “Comprehending Comprehensions”
  17. My new course, “Understanding and Mastering Git,” is now available
  18. Four ways to assign variables in Python
  19. Using Python to delete files based on other files’ names

2017 26

  1. Less content + more exercises = better learning + more satisfaction. That’s Weekly Python Exercise.
  2. Registration closes soon for Weekly Python Exercise
  3. Focus on the process: Your Python questions, answered
  4. Registration is open for the January 2018 cohort of “Weekly Python Exercise”
  5. A very sad day — the end of Linux Journal
  6. Black Friday sale: 40% off my Python and Git books and courses
  7. Aha! Preview this week’s live, online Python courses
  8. Announcing: Three new live courses, to level up your Python and Git skills
  9. Level up your Python, with three new courses
  10. My favorite terrible Python error message
  11. foo(y=y), and similar code that confuses Python newbies
  12. Where can you practice (and improve) your Python skills?
  13. Globbing and Python’s “subprocess” module
  14. Five Python function parameters you should know and use
  15. One-day birthday sale — on July 14th, get 47% off my courses, books, and subscriptions
  16. Announcing: Three live Python courses
  17. Raw strings to the rescue!
  18. Announcing: Weekly Python Exercise
  19. Boolean indexing in NumPy and Pandas: A free e-mail course for aspiring data scientists
  20. 2+2 might be 4, but what is True+True?
  21. Python function brain transplants
  22. The five-minute guide to setting up a Jupyter notebook server
  23. A short Python class puzzle
  24. Data science + machine learning + Python course in Shanghai
  25. Announcing: Trainer Weekly, practical advice for technical trainers
  26. Free download: Cheat sheet for Python data structures

2016 14

  1. The (lack of a) case against Python 3
  2. Why you should read “Weapons of Math Destruction”
  3. Implementing “zip” with list comprehensions
  4. Fun with floats
  5. Announcing: An online community for technical trainers
  6. Speedy string concatenation in Python
  7. Want to learn Chinese?
  8. Another free regexp Q&A webinar!
  9. Free Webinar: Regexp Q&A
  10. Yes, you can master regular expressions!
  11. Using regexps in PostgreSQL
  12. All 50 “Practice Makes Python” screencasts are complete!
  13. Free Webinar: Pandas and Matplotlib
  14. My interview with the Freelance Transformation podcast

2015 21

  1. Reminder: Free Webinar on data science in Python
  2. Free Webinar: Data science with Python on December 8th
  3. Shark Tank increased our traffic by 1000x. Here’s how we handled it.
  4. Updated ebook: Jewish Guide to Visiting China
  5. Python’s objects and classes — a visual guide
  6. Registration is open for my October Webinars (about regexps and technical training)
  7. Now available: My interview on “Developer on Fire” about training programmers
  8. In PostgreSQL, as in life, don’t wait too long to commit
  9. Announcing: Coaching for technical trainers
  10. Understanding nested list comprehensions in Python
  11. Want to understand Python’s comprehensions? Think in Excel or SQL.
  12. Why you should almost never use “is” in Python
  13. Free Webinar on June 23rd: Introduction to Regular Expressions
  14. New ebook: Jewish guide to visiting China
  15. Free one-hour Webinar about Python’s magic methods on May 6th
  16. Is it hashable? Fun and games with hashing in Python
  17. Free Webinar in object-oriented Python on April 1st, 2015
  18. How not to write an error message
  19. A quick introduction to implementing Python iterators
  20. If you don’t use “with”, when does Python close files? The answer is: It depends.
  21. My latest side project: DailyTechVideo.com, posting new conference videos every day

2014 39

  1. All 50 exercises in “Practice Makes Python” are complete! (Plus, a sample exercise about taxes in Freedonia)
  2. “Practice Makes Python” is now available for early-bird purchase
  3. In Python, it’s all about the attributes
  4. Announcing: A free Webinar, and two online courses (functional Python and OO Python)
  5. Sorting lists of dicts — an exercise from “Practice Makes Python”
  6. Thinking with “map”
  7. The relative speeds of str.format and %
  8. Teaching an old dog new tricks — or, how I learned to love Python’s str.format, and gave up on %
  9. Three Pythonic products: A (free) Webinar, a course, and an ebook
  10. The easiest way to return to the last Git branch
  11. Remember: Don’t mix = and NULL
  12. Book Review: The Undercover Economist Strikes Back
  13. Turning a PostgreSQL array to rows
  14. Turning PostgreSQL rows into arrays
  15. Looking in PostgreSQL arrays with ANY
  16. The real questions to ask offshore developers
  17. PostgreSQL array indexes and length
  18. Learning to love PostgreSQL arrays
  19. Control-R, my favorite Unix shell command
  20. Starting a new software project? Don’t start coding right away.
  21. Summary of my “reduce” series
  22. Implementing “filter” with “reduce”, in Ruby and Python
  23. Implementing “map” with “reduce”, in Ruby and Python
  24. Creating Ruby hashes with “reduce”
  25. Creating Python dictionaries with “reduce”
  26. Creating collections with “reduce”
  27. Implementing “min” and “max” with “reduce”
  28. Calculating Scrabble scores with “reduce”
  29. Understanding “reduce” (first in a series)
  30. If you build it, they will come — but they might hate you
  31. Good intentions, unexpected results: Mailing lists and DMARC
  32. rvm do
  33. Announcing: Teaching to Code, a community of programming instructors
  34. Teaching and acting (or, why I don’t plan to sell recorded classes in the near future)
  35. Benchmarking old-style and new-style Python classes
  36. = and = aren’t equal
  37. Last call for my online Python class
  38. Ruby and Python and Felix and Oscar
  39. Making Python’s __init__ method magical

2013 5

  1. Python scoping e-mail course
  2. Fun with Python scoping rules
  3. Don’t use double quotes in PostgreSQL
  4. Convention over confusion
  5. Hello, world (again)