PYTHON FOR
DATA ANALYTICS
Interview Preparation Guide
NumPy • Pandas • Matplotlib • Seaborn • Selenium • BeautifulSoup
Core concepts • Cheat sheets • Common interview Q&A
Contents
1. NumPy
Arrays, broadcasting, vectorization, axes, missing values
2. Pandas
Series/DataFrame, indexing, groupby, merging, reshaping
3. Matplotlib
Figures & Axes, subplots, exporting, dual axes
4. Seaborn
Statistical & categorical plots, heatmaps, facets
5. Selenium
Browser automation, waits, locators, dynamic pages
6. BeautifulSoup
HTML parsing, tag search, tables, pagination
7. Quick-Reference: Which Tool When?
A one-page decision guide
How to use this guide
Each library section opens with a short overview, a quick cheat-sheet of the functions/methods you're most
likely to need, and then a set of realistic interview questions with concise model answers — several include
short code snippets you can practice typing out by hand, since many interviews include a live-coding
component.
Python for Data Analytics — Interview Prep Page 2
NumPy
Numerical computing & the n-dimensional array (ndarray)
Overview
NumPy is the foundation of the Python data-science stack. It introduces the ndarray, a fast, memory-efficient,
multi-dimensional array, and provides vectorized operations that replace slow Python for-loops with calls to
optimized C code. Pandas, scikit-learn, and most ML/DL frameworks are built on top of NumPy arrays, so a
solid grasp of it is assumed in almost every data analytics interview.
Cheat Sheet
[Link] / [Link] / [Link] Create arrays from data, or pre-filled with 0s / 1s.
[Link] / [Link] Sequence by step size vs. by fixed number of points.
.shape / .ndim / .dtype Dimensions, number of axes, and data type of an array.
.reshape() / .ravel() Change shape without copying data where possible.
Slicing & boolean indexing arr[1:3], arr[arr > 5] — select by position or condition.
Broadcasting Automatically stretches smaller arrays to match shapes in operations.
axis=0 / axis=1 0 = operate down rows (column-wise result); 1 = across columns.
[Link] / [Link] Conditional selection; distinct values + counts.
[Link] / vstack / Combine arrays along an existing or new axis.
hstack
[Link] / [Link] / @ Linear algebra: matrix multiply, inverse, determinant.
[Link], [Link], Represent and safely aggregate over missing values.
[Link]
[Link]() Make random number generation reproducible.
Interview Questions & Answers
Q1. What is NumPy and why use it instead of native Python lists?
NumPy stores data in contiguous blocks of memory of a single type and runs operations in compiled C, so
array math is vectorized and far faster than looping over Python lists. It also supports broadcasting, slicing, and
linear algebra that lists don't natively support.
Python for Data Analytics — Interview Prep Page 3
Q2. Explain broadcasting with an example.
Broadcasting lets NumPy perform element-wise operations on arrays of different shapes by virtually 'stretching'
the smaller array, without actually copying data, as long as their trailing dimensions are equal or one of them is
1.
import numpy as np
a = [Link]([[1, 2, 3],
[4, 5, 6]]) # shape (2, 3)
b = [Link]([10, 20, 30]) # shape (3,)
print(a + b)
# [[11 22 33]
# [14 25 36]] -> b is broadcast across both rows
Q3. What is the difference between a view and a copy in NumPy?
A view shares the same underlying memory as the original array (basic slicing returns a view), so modifying it
changes the original. A copy is an independent array in new memory (created via .copy(), fancy indexing, or
boolean indexing). Use [Link] or np.shares_memory() to check which one you have.
Q4. Difference between reshape() and resize()?
reshape() returns a new view/array with a different shape but the same total number of elements (raises an
error if sizes don't match) and does not modify the original in place. resize() ([Link]) changes the
array's shape in place, and can pad with zeros or truncate data if the new size doesn't match.
Q5. How does NumPy achieve such large speed-ups over plain Python loops?
Three reasons: (1) data is stored in contiguous, homogeneously-typed memory, removing per-element type
checks; (2) operations are vectorized — implemented as compiled C loops (ufuncs) rather than interpreted
Python bytecode; (3) it can exploit CPU-level optimizations (SIMD) and avoids Python's per-object overhead.
Q6. What does the axis parameter mean in aggregation functions like sum() or mean()?
axis specifies which dimension is collapsed. For a 2-D array, axis=0 aggregates down the rows producing one
value per column, while axis=1 aggregates across the columns producing one value per row.
arr = [Link]([[1, 2], [3, 4], [5, 6]])
[Link](axis=0) # -> [9, 12] (column sums)
[Link](axis=1) # -> [3, 7, 11] (row sums)
Q7. How do you handle NaN values in a NumPy array?
Use [Link]() to detect them, and NaN-aware aggregation functions such as [Link](), [Link](), or
[Link]() to compute statistics while ignoring NaNs. np.nan_to_num() can replace NaNs/infs with a chosen
finite value.
Q8. [Link]() vs [Link]() — what's the difference?
[Link]() always creates a new array (copies data by default). [Link]() converts the input to an array but
avoids copying if the input is already an ndarray of the same dtype — useful for writing functions that accept
array-like input without unnecessary memory duplication.
Python for Data Analytics — Interview Prep Page 4
Pandas
Labeled, tabular data manipulation — Series & DataFrame
Overview
Pandas is the primary tool analysts use to load, clean, transform, and summarize tabular data. It wraps NumPy
arrays with row/column labels (an Index) and adds high-level operations like joins, group-by aggregation,
pivoting, and time-series handling. Most analytics interviews include at least one live pandas coding exercise.
Cheat Sheet
pd.read_csv / read_excel / Load data from common sources into a DataFrame.
read_sql
.head() / .info() / .describe() Quick look at rows, dtypes/nulls, and summary stats.
.loc[] vs .iloc[] Label-based vs. integer position-based indexing.
.isnull().sum() / .fillna() / Detect, impute, or remove missing values.
.dropna()
.groupby() Split-apply-combine: group rows, then aggregate/transform each group.
merge() / join() / concat() Combine DataFrames by keys, by index, or by stacking.
pivot_table() / pivot() / melt() Reshape data wide<->long and aggregate while doing so.
.apply() / .map() / Apply a function over rows/cols, a Series, or all cells.
.applymap()
.sort_values() / Order rows by column(s); count frequency of values.
.value_counts()
.duplicated() / Flag or remove duplicate rows.
.drop_duplicates()
.astype() / pd.to_datetime() Convert column data types, including string-to-date.
.query() / boolean masks Filter rows with a readable expression or condition array.
Interview Questions & Answers
Q1. What is the difference between a Series and a DataFrame?
A Series is a single labeled, one-dimensional array (like one column with an index). A DataFrame is a
two-dimensional, labeled table — essentially a dict of Series sharing the same index, with both row and column
labels.
Python for Data Analytics — Interview Prep Page 5
Q2. loc[] vs iloc[] — when do you use each?
loc[] selects rows/columns by label (name), and its slices are inclusive of the end label. iloc[] selects strictly by
integer position, with Python-style exclusive-end slicing, regardless of what the labels are.
[Link][2:4, 'sales'] # rows labeled 2 through 4 inclusive
[Link][2:4, 1] # rows at positions 2,3 (4 excluded)
Q3. How do you handle missing data in a DataFrame?
First quantify it with [Link]().sum(). Then either drop rows/columns with dropna() (when missingness is
small/random), or impute with fillna() using a constant, mean/median/mode, or a forward/backward fill —
choosing a strategy based on the column's meaning and how much data would be lost.
Q4. merge(), join(), and concat() — how are they different?
merge() combines DataFrames on one or more shared key columns (like a SQL JOIN, with
how='inner'/'left'/'right'/'outer'). join() is similar but combines primarily on the index. concat() simply stacks
DataFrames along an axis (rows or columns) without matching on keys, only aligning on the existing
index/columns.
Q5. Explain what happens internally during a groupby() operation.
groupby implements split-apply-combine: pandas first splits the DataFrame into groups based on the key
column(s), then applies a function (e.g. sum, mean, a custom function) independently to each group, and finally
combines the results back into a single Series/DataFrame.
[Link]('region')['sales'].sum()
[Link](['region', 'category']).agg(
total=('sales', 'sum'),
avg_price=('price', 'mean')
)
Q6. apply(), map(), and applymap() — what's the difference?
map() works element-wise on a single Series (e.g. mapping codes to labels). apply() works on a Series
(element-wise) or a DataFrame, where it's typically used to run a function down each row or column.
applymap() applies a function element-wise to every single cell of a DataFrame.
Q7. How would you reduce the memory footprint of a large DataFrame?
Downcast numeric columns with pd.to_numeric(..., downcast=...), convert low-cardinality text columns to the
'category' dtype, drop unused columns early, and read large files in chunks with chunksize= in read_csv() or
only the needed columns via usecols=.
Q8. What is a MultiIndex and when would you use one?
A MultiIndex is a hierarchical index with multiple levels (e.g. region then store), letting you represent
higher-dimensional data in a 2-D structure. It's useful after a groupby on multiple columns or a pivot_table,
enabling intuitive slicing like [Link]['West', 'Store_12'].
Python for Data Analytics — Interview Prep Page 6
Q9. Difference between pivot() and pivot_table()?
pivot() reshapes data from long to wide format but requires unique index/column combinations and does no
aggregation — it errors on duplicates. pivot_table() does the same reshape but also aggregates (default mean)
when there are duplicate combinations, making it more flexible for real-world data.
Q10. How would you find and remove duplicate rows?
Use [Link]() to get a boolean mask of duplicate rows (optionally on a subset of columns via subset=),
then df.drop_duplicates(subset=..., keep='first') to remove them, choosing which occurrence to keep.
Python for Data Analytics — Interview Prep Page 7
Matplotlib
The low-level plotting engine behind most Python visualization
Overview
Matplotlib is the original Python plotting library and the engine underneath pandas' .plot() and most of Seaborn.
It offers two ways to build a chart: the quick, stateful pyplot interface ([Link](), [Link](), ...) and the more
explicit, recommended object-oriented interface using Figure and Axes objects — important for multi-panel or
production-quality charts.
Cheat Sheet
[Link] / scatter / bar / hist Core chart types: line, scatter, bar, histogram.
fig, ax = [Link]() Object-oriented interface: explicit Figure & Axes objects.
[Link](nrows, ncols) Create a grid of multiple Axes in one Figure.
ax.set_title / set_xlabel / Annotate a specific Axes (OOP style).
set_ylabel
[Link]() / [Link]() Show a legend mapping colors/markers to labels.
[Link](figsize=(w,h)) Control the overall size of the figure in inches.
[Link]('[Link]', Export a chart to a high-resolution image file.
dpi=300)
[Link]('seaborn-v0_8') Apply a built-in visual theme to all following plots.
[Link]() Add a second y-axis sharing the same x-axis.
plt.tight_layout() Auto-adjust spacing so labels/titles don't overlap.
Interview Questions & Answers
Q1. What is the difference between the pyplot interface and the object-oriented (fig, ax) interface?
[Link]()-style calls operate on an implicit 'current' figure/axes — quick for a single simple chart but error-prone
with multiple subplots. The OOP interface creates explicit fig, ax objects and calls methods on them directly
([Link](), ax.set_title()), giving precise control — the recommended approach for anything beyond a single
quick plot.
fig, ax = [Link](figsize=(6, 4))
[Link](x, y, label='revenue')
ax.set_title('Monthly Revenue')
[Link]()
Python for Data Analytics — Interview Prep Page 8
Q2. How do you create multiple subplots in one figure?
[Link](nrows, ncols) returns a Figure and an array of Axes objects; each Axes is plotted on
independently, then a single [Link]()/savefig() displays or exports the whole grid.
fig, axes = [Link](1, 2, figsize=(10, 4))
axes[0].plot(x, y1)
axes[1].bar(categories, values)
Q3. Figure vs Axes vs Axis — what do these terms mean?
A Figure is the entire canvas/window that can hold one or more plots. An Axes is one individual plot/chart within
that figure (with its own title, data, and legend). An Axis refers to one of the x or y number lines on an Axes —
confusingly named, but a common interview gotcha.
Q4. How would you save a publication-quality, high-resolution chart?
Call [Link]('[Link]', dpi=300, bbox_inches='tight') — dpi controls resolution and bbox_inches='tight'
trims excess whitespace around the figure. Vector formats like PDF or SVG are preferred when the chart
needs to scale without pixelation.
Q5. How do you add a second y-axis to compare two metrics with different scales?
Create a twin Axes that shares the x-axis with [Link](), then plot the second series on that new axes object
so it gets its own independent y-scale.
fig, ax1 = [Link]()
[Link](months, revenue, color='tab:blue')
ax2 = [Link]()
[Link](months, growth_pct, color='tab:orange')
Q6. What's the difference between a bar chart and a histogram?
A bar chart shows values for discrete/categorical groups, where bar order and gaps are usually meaningful. A
histogram bins a single continuous numeric variable into contiguous ranges and shows the frequency/count
within each bin, so the bars touch and represent a distribution rather than separate categories.
Python for Data Analytics — Interview Prep Page 9
Seaborn
Statistical, DataFrame-aware visualization built on Matplotlib
Overview
Seaborn sits on top of Matplotlib and is designed to work directly with pandas DataFrames. It provides attractive
default styling and high-level functions for common statistical plots — distributions, categorical comparisons,
and correlation heatmaps — with far less boilerplate code than plain Matplotlib.
Cheat Sheet
[Link] / lineplot Relationship plots between two numeric variables.
[Link] / boxplot / Compare a numeric variable across categories.
violinplot
[Link] / kdeplot Visualize the distribution of a single numeric variable.
[Link]([Link]()) Color-coded matrix, commonly used for correlation analysis.
[Link](df) Grid of pairwise scatterplots for all numeric columns at once.
hue / style / size parameters Map an extra categorical/numeric variable to color/shape.
[Link] / [Link] Split one plot into a grid of subplots by a category.
sns.set_theme() / set_style() Apply a consistent visual theme across all plots.
[Link]() Bar chart of counts/frequency for a categorical column.
Interview Questions & Answers
Q1. How is Seaborn different from Matplotlib if it's built on top of it?
Matplotlib is low-level and general-purpose — you build a chart piece by piece. Seaborn provides high-level
functions tailored to statistical analysis that accept a DataFrame and column names directly, handle
grouping/aggregation and color mapping automatically, and apply more polished default styling — at the cost of
some fine-grained control, which you can still reach via the underlying Matplotlib Axes object it returns.
Q2. When would you use a boxplot vs. a violinplot?
A boxplot summarizes a distribution with five-number-summary statistics (median, quartiles, whiskers, outliers)
— good for quickly comparing spread/outliers across groups. A violinplot shows the same comparison but also
draws the full estimated distribution shape (via a kernel density estimate), which is more informative when a
distribution is multimodal but takes more space and explanation.
Python for Data Analytics — Interview Prep Page 10
Q3. How would you visualize correlation between numeric variables in a dataset?
Compute the correlation matrix with [Link]() and pass it to [Link](), typically with annot=True to print the
coefficients on each cell and a diverging colormap (e.g. 'coolwarm') so positive and negative correlations are
visually distinct.
corr = df.select_dtypes('number').corr()
[Link](corr, annot=True, cmap='coolwarm', center=0)
Q4. What does the hue parameter do, and why is it useful?
hue maps an additional categorical column to color within the same plot, letting you compare an extra
dimension (e.g. compare 'sales vs. month' separately by 'region') without manually looping and plotting multiple
series.
[Link](data=df, x='month', y='sales', hue='region')
Q5. How do you create a grid of plots split by a categorical variable?
Use [Link]() or [Link](), specifying col= and/or row= with a categorical column; Seaborn
automatically creates one subplot per category and lays them out in a grid, keeping axis scales consistent for
easy comparison.
[Link](data=df, x='day', y='total_bill',
col='time', kind='box')
Q6. How do you handle overplotting when a scatterplot has thousands of points?
Reduce opacity with alpha=, use [Link]() or a hexbin/2-D histogram instead of raw points to show density
rather than individual marks, or take a representative random sample of the data before plotting.
Python for Data Analytics — Interview Prep Page 11
Selenium
Browser automation for dynamic, JavaScript-rendered websites
Overview
Selenium drives a real browser programmatically, so it can click buttons, fill forms, scroll, and — critically for
data analytics roles — render JavaScript-heavy pages before scraping them, which static tools like
requests/BeautifulSoup cannot do on their own. It's commonly paired with BeautifulSoup or pandas once the
page HTML has loaded.
Cheat Sheet
[Link]() / Launch a controlled browser session.
Firefox()
driver.find_element([Link], Locate a single element by ID, CSS, XPATH, etc.
...)
driver.find_elements(...) Locate all matching elements as a list.
[Link] / CSS_SELECTOR / Different strategies for locating elements.
XPATH / NAME
[Link]() / send_keys() Simulate a mouse click or keyboard typing.
WebDriverWait + Explicit wait until a condition (e.g. visible) is true.
expected_conditions
driver.implicitly_wait(second Global, less precise wait applied to all lookups.
s)
Select(element) Helper class for interacting with dropdowns.
driver.switch_to.frame() / Move control context into an iframe or new tab.
window()
Options(); options.add_argu Run the browser without a visible UI.
ment('--headless')
Interview Questions & Answers
Q1. When would you reach for Selenium instead of requests + BeautifulSoup?
requests + BeautifulSoup only see the raw HTML returned by the server. If the data you need is rendered
client-side by JavaScript after the initial page load (common with React/Vue/Angular sites, infinite scroll, or
content behind a login/click), you need a real browser engine — which is what Selenium provides.
Python for Data Analytics — Interview Prep Page 12
Q2. Implicit wait vs. explicit wait — why is explicit generally preferred?
implicitly_wait() sets one global timeout applied to every find_element call, which can mask slow elements or
waste time waiting unnecessarily. An explicit wait (WebDriverWait combined with expected_conditions) waits
only as long as needed for a specific, named condition on a specific element, making scripts faster and more
reliable, and the two should not be mixed.
from [Link] import WebDriverWait
from [Link] import expected_conditions as EC
from [Link] import By
elem = WebDriverWait(driver, 10).until(
EC.presence_of_element_located(([Link], 'results'))
)
Q3. What locator strategies are available, and which is the most robust?
[Link], [Link], By.CLASS_NAME, By.TAG_NAME, By.CSS_SELECTOR, [Link], and By.LINK_TEXT.
ID is fastest/most stable when present. CSS_SELECTOR is generally preferred over XPATH for readability and
speed; XPATH is reserved for cases needing to navigate by text content or complex relative positions that CSS
can't express.
Q4. How do you interact with a dropdown () element?
Wrap the located WebElement in Selenium's Select helper class, then choose an option by visible text, value,
or index rather than trying to click manually.
from [Link] import Select
dropdown = Select(driver.find_element([Link], 'country'))
dropdown.select_by_visible_text('India')
Q5. How would you scrape data from a page with infinite scroll?
Loop: execute JavaScript to scroll to the bottom of the page (driver.execute_script('[Link](0,
[Link])')), wait for new content to load, and repeat until the page height stops increasing
(or a max number of iterations is reached) before extracting the fully-loaded HTML.
Q6. Why and how do you run Selenium in headless mode?
Headless mode runs the browser without rendering a visible UI window, which is faster and uses less memory
— essential for running scrapers on servers/CI without a display. It's enabled via browser Options before
creating the driver.
from [Link] import Options
opts = Options()
opts.add_argument('--headless=new')
driver = [Link](options=opts)
Q7. How do you handle JavaScript alerts or switch between browser tabs?
For native browser alerts/confirms, use driver.switch_to.alert and then .accept() or .dismiss(). For multiple
tabs/windows, driver.window_handles lists all open window handles, and driver.switch_to.window(handle)
moves control to a specific one.
Python for Data Analytics — Interview Prep Page 13
BeautifulSoup
Parsing and extracting data from static HTML/XML
Overview
BeautifulSoup turns raw HTML/XML text (typically fetched with the requests library) into a navigable parse tree,
making it easy to search for tags, read their attributes and text, and walk the document structure. It's the
standard tool for scraping static pages where Selenium's overhead isn't needed.
Cheat Sheet
BeautifulSoup(html, Parse a string of HTML into a navigable tree.
'[Link]')
.find(tag, attrs) Return the first matching tag.
.find_all(tag, attrs) Return a list of every matching tag.
.select('[Link]') Locate elements using CSS selector syntax.
.get_text() / .text Extract the visible text content from a tag (and children).
tag['href'] / [Link]('href') Read an HTML attribute's value from a tag.
.parent / .next_sibling / Navigate up, sideways, or down the parse tree.
.children
'lxml' / '[Link]' / Different underlying parser engines to choose from.
'html5lib'
Interview Questions & Answers
Q1. requests + BeautifulSoup vs. Selenium — how do you choose?
If the data is present in the initial server response (view-source shows it), requests + BeautifulSoup is simpler,
faster, and lighter on resources. If the content only appears after JavaScript executes in a browser, you need
Selenium (or an API the JS calls under the hood) to render the page first.
Q2. find() vs. find_all() — what's the difference?
find() returns only the first matching tag (or None if nothing matches). find_all() returns a list of every matching
tag in the document, which you then typically loop over.
first_price = [Link]('span', class_='price')
all_prices = soup.find_all('span', class_='price')
Python for Data Analytics — Interview Prep Page 14
Q3. How would you extract every link from a page?
Find all anchor tags and read each one's href attribute, guarding against tags that might not have an href (e.g.
anchors used only as scroll targets).
links = [[Link]('href') for a in soup.find_all('a') if [Link]('href')]
Q4. How do you parse an HTML directly into a pandas DataFrame?
For straightforward tables, pandas' own pd.read_html(html_string) extracts every on the page into a list of
DataFrames automatically. For more irregular tables, it's often easier to manually loop over / tags found via
BeautifulSoup and build rows by hand.
import pandas as pd
tables = pd.read_html(str([Link]('table')))
df = tables[0]
Q5. [Link] vs. lxml vs. html5lib — how do these parsers differ?
[Link] is Python's built-in parser — no extra install, but slower and less lenient with malformed markup.
lxml is a fast C-based parser, generally recommended for performance, and handles minor HTML errors well.
html5lib is the slowest but most forgiving and spec-accurate, parsing pages exactly as a real browser would,
which helps with badly broken HTML.
Q6. How do you handle badly malformed HTML?
Switch to a more lenient parser like 'html5lib', since it follows the same error-correction rules browsers use. If
specific tags are still hard to match, fall back to navigating by structure (parent/sibling relationships) or using a
regular expression as the search pattern passed into find_all().
Q7. How would you scrape content spread across multiple paginated pages?
Identify the URL pattern for pagination (e.g. a page= or offset= query parameter, or a 'Next' link's href), loop
while incrementing that parameter or following the 'Next' link, re-parsing each page's HTML, and stop once no
further page/Next link is found.
Python for Data Analytics — Interview Prep Page 15
Quick Reference — Which Tool, When?
Numerical computation on NumPy
arrays/matrices
Loading, cleaning, joining, Pandas
summarizing tabular data
Full manual control over a Matplotlib
custom/complex chart
Fast statistical chart directly Seaborn
from a DataFrame
Scraping a static page (data requests + BeautifulSoup
visible in raw HTML)
Scraping a JS-rendered Selenium
page, or automating
clicks/forms
End-to-end pipeline: scrape Selenium/BS4 → Pandas/NumPy → Matplotlib/Seaborn
→ clean → analyze →
visualize
A Sample End-to-End Question
Q1. Walk me through how you'd scrape a product listing page and turn it into insights.
Typical answer flow: (1) inspect the page — if data is in the raw HTML, use requests + BeautifulSoup; if it's
JS-rendered or paginated via infinite scroll, use Selenium instead; (2) extract fields (name, price, rating) into a
list of dicts and load them into a pandas DataFrame; (3) clean the data — fix dtypes, strip currency symbols,
handle missing ratings; (4) use NumPy/Pandas for aggregation (e.g. average price per category); (5) visualize
the findings with Matplotlib/Seaborn (e.g. a bar chart of average price by category, or a heatmap of
correlations); (6) summarize the business takeaway.
Good luck with your interview!
Tip: in live-coding rounds, narrate your thought process out loud, write small testable steps instead of one large
block, and don't hesitate to mention the exact method name even if you need to glance at how its arguments
are ordered.
Python for Data Analytics — Interview Prep Page 16