1. Big Picture
pandas is excellent for data analysis in Python. SQL is excellent for asking structured questions from tables. When we combine them, we get a powerful workflow.
What you will learn
- How to create a pandas DataFrame.
- How to create a SQLite database using Python.
- How to save a DataFrame as a SQL table.
- How to run SQL queries from pandas.
- How to use
SELECT,WHERE,ORDER BY,GROUP BYandJOIN. - How to compare SQL queries with pandas commands.
- How to use SQL result data for model training.
- How to save query results and trained models.
2. Why Use SQL with Pandas?
pandas and SQL both work with tabular data, but they are useful in different ways.
| Tool | Best for | Example use |
|---|---|---|
| SQL | Querying data from databases | Find all students with marks greater than 70 |
| pandas | Cleaning, analysis, charts and model preparation | Fill missing values, create graphs, prepare X and y |
| SQL + pandas | Complete data workflow | Pull filtered data from database and train a model |
Simple comparison
SQL asks questions like this:
SELECT name, marks
FROM students
WHERE marks >= 70;
pandas asks similar questions like this:
result = df[df["marks"] >= 70][["name", "marks"]]
3. Setup
For this lesson, we will use sqlite3, which is included
with Python. We do not need to install a separate database server.
Import libraries
import sqlite3
import pandas as pd
import matplotlib.pyplot as plt
import joblib
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression
Explanation of each library
| Library | Purpose |
|---|---|
sqlite3 |
Creates and connects to SQLite databases. |
pandas |
Creates DataFrames and runs SQL queries into DataFrames. |
matplotlib |
Makes charts. |
joblib |
Saves and loads trained machine learning models. |
scikit-learn |
Provides machine learning models and train-test split. |
Install needed libraries
If these libraries are not installed on your local computer, use:
pip install pandas matplotlib scikit-learn joblib
You do not need to install sqlite3 separately because it
usually comes with Python.
4. Creating Data and Saving It into SQL
First, we will create a pandas DataFrame. Then we will save that DataFrame into a SQLite database table.
4.1 Create a student DataFrame
import pandas as pd
students_data = {
"student_id": [1, 2, 3, 4, 5, 6, 7, 8],
"name": ["Amit", "Ravi", "Sita", "Meena", "Kabir", "Anu", "Farhan", "Pooja"],
"city": ["Varanasi", "Lucknow", "Varanasi", "Delhi", "Lucknow", "Delhi", "Varanasi", "Lucknow"],
"hours": [1, 2, 3, 4, 5, 6, 7, 8],
"attendance": [55, 60, 65, 70, 78, 85, 90, 95],
"marks": [35, 42, 50, 58, 70, 80, 88, 96]
}
students_df = pd.DataFrame(students_data)
print(students_df)
4.2 Create a database connection
import sqlite3
connection = sqlite3.connect("school.db")
This creates a file named school.db. If the file already
exists, Python connects to it. If it does not exist, Python creates it.
4.3 Save DataFrame into SQL table
students_df.to_sql(
"students",
connection,
if_exists="replace",
index=False
)
Explanation of to_sql()
| Part | Meaning |
|---|---|
"students" |
Name of the SQL table. |
connection |
The database connection where table will be saved. |
if_exists="replace" |
If table already exists, replace it. |
index=False |
Do not save pandas index as a separate SQL column. |
if_exists="replace" deletes the old table and creates a new one.
Use it while learning, but be careful in real projects.
Other values of if_exists
| Value | Meaning |
|---|---|
"replace" |
Delete old table and create new table. |
"append" |
Add rows to existing table. |
"fail" |
Give error if table already exists. |
5. Reading SQL Data into Pandas
The most important pandas command for SQL is:
pd.read_sql_query()
It runs a SQL query and returns the result as a pandas DataFrame.
5.1 Read full table
query = "SELECT * FROM students"
result_df = pd.read_sql_query(query, connection)
print(result_df)
Explanation
| Part | Meaning |
|---|---|
SELECT * |
Select all columns. |
FROM students |
Use the students table. |
pd.read_sql_query(query, connection) |
Run SQL and bring result into pandas. |
5.2 Check the returned DataFrame
print(result_df.head())
print(result_df.info())
print(result_df.describe())
Once the SQL result comes into pandas, it behaves like any normal DataFrame.
6. SQL SELECT in Pandas
SELECT is used to choose columns from a SQL table.
6.1 Select all columns
query = """
SELECT *
FROM students
"""
df = pd.read_sql_query(query, connection)
print(df)
6.2 Select specific columns
query = """
SELECT name, city, marks
FROM students
"""
df = pd.read_sql_query(query, connection)
print(df)
6.3 Rename output columns using alias
query = """
SELECT
name AS student_name,
marks AS final_marks
FROM students
"""
df = pd.read_sql_query(query, connection)
print(df)
AS gives a temporary name to a column in the output.
6.4 Create calculated columns
query = """
SELECT
name,
marks,
marks + 5 AS marks_after_bonus
FROM students
"""
df = pd.read_sql_query(query, connection)
print(df)
SQL can calculate new columns during query time.
7. SQL WHERE in Pandas
WHERE is used to filter rows.
7.1 Students with marks 70 or above
query = """
SELECT name, city, marks
FROM students
WHERE marks >= 70
"""
df = pd.read_sql_query(query, connection)
print(df)
7.2 Students from Lucknow
query = """
SELECT *
FROM students
WHERE city = 'Lucknow'
"""
df = pd.read_sql_query(query, connection)
print(df)
7.3 Multiple conditions with AND
query = """
SELECT name, hours, attendance, marks
FROM students
WHERE hours >= 5 AND attendance >= 80
"""
df = pd.read_sql_query(query, connection)
print(df)
7.4 Multiple conditions with OR
query = """
SELECT name, city, marks
FROM students
WHERE city = 'Delhi' OR marks >= 90
"""
df = pd.read_sql_query(query, connection)
print(df)
7.5 Sorting with ORDER BY
query = """
SELECT name, city, marks
FROM students
ORDER BY marks DESC
"""
df = pd.read_sql_query(query, connection)
print(df)
| SQL word | Meaning |
|---|---|
WHERE |
Filters rows. |
AND |
Both conditions must be true. |
OR |
At least one condition must be true. |
ORDER BY |
Sorts result. |
DESC |
Descending order, biggest first. |
ASC |
Ascending order, smallest first. |
8. SQL GROUP BY in Pandas
GROUP BY is used when we want summary results.
For example: average marks by city.
8.1 Average marks by city
query = """
SELECT
city,
AVG(marks) AS average_marks
FROM students
GROUP BY city
"""
df = pd.read_sql_query(query, connection)
print(df)
8.2 Count students city by city
query = """
SELECT
city,
COUNT(*) AS total_students
FROM students
GROUP BY city
"""
df = pd.read_sql_query(query, connection)
print(df)
8.3 Minimum and maximum marks by city
query = """
SELECT
city,
MIN(marks) AS lowest_marks,
MAX(marks) AS highest_marks
FROM students
GROUP BY city
"""
df = pd.read_sql_query(query, connection)
print(df)
8.4 Filtering groups with HAVING
query = """
SELECT
city,
AVG(marks) AS average_marks
FROM students
GROUP BY city
HAVING AVG(marks) >= 70
"""
df = pd.read_sql_query(query, connection)
print(df)
WHERE filters rows before grouping.
HAVING filters groups after grouping.
| SQL function | Meaning |
|---|---|
COUNT() |
Counts rows. |
AVG() |
Finds average. |
MIN() |
Finds smallest value. |
MAX() |
Finds largest value. |
SUM() |
Adds values. |
9. SQL JOIN in Pandas
A JOIN combines data from two tables.
This is one of the most powerful parts of SQL.
9.1 Create another DataFrame
fees_data = {
"student_id": [1, 2, 3, 4, 5, 6, 7, 8],
"fees_paid": [5000, 4500, 5000, 4000, 3000, 5000, 4500, 5000],
"scholarship": [0, 500, 0, 1000, 1500, 0, 500, 0]
}
fees_df = pd.DataFrame(fees_data)
fees_df.to_sql(
"fees",
connection,
if_exists="replace",
index=False
)
Now we have two tables:
studentsfees
9.2 INNER JOIN
query = """
SELECT
students.student_id,
students.name,
students.city,
students.marks,
fees.fees_paid,
fees.scholarship
FROM students
INNER JOIN fees
ON students.student_id = fees.student_id
"""
df = pd.read_sql_query(query, connection)
print(df)
Explanation
| Part | Meaning |
|---|---|
INNER JOIN fees |
Join students table with fees table. |
ON students.student_id = fees.student_id |
Match rows using student_id from both tables. |
students.name |
Use name column from students table. |
fees.fees_paid |
Use fees_paid column from fees table. |
9.3 JOIN with condition
query = """
SELECT
students.name,
students.city,
students.marks,
fees.fees_paid,
fees.scholarship
FROM students
INNER JOIN fees
ON students.student_id = fees.student_id
WHERE students.marks >= 70
"""
df = pd.read_sql_query(query, connection)
print(df)
10. Same Task: Pandas vs SQL
Let us compare common operations in pandas and SQL.
| Task | SQL | pandas |
|---|---|---|
| Select all rows | SELECT * FROM students |
df |
| Select columns | SELECT name, marks FROM students |
df[["name", "marks"]] |
| Filter rows | WHERE marks >= 70 |
df[df["marks"] >= 70] |
| Sort | ORDER BY marks DESC |
df.sort_values("marks", ascending=False) |
| Average | AVG(marks) |
df["marks"].mean() |
| Group average | GROUP BY city |
df.groupby("city")["marks"].mean() |
| Join tables | INNER JOIN |
pd.merge() |
When should we use SQL?
- When data is already inside a database.
- When we want to fetch only selected rows and columns.
- When tables need to be joined.
- When the dataset is too large to load fully into pandas.
When should we use pandas?
- When data is already in a DataFrame.
- When we need cleaning and transformation.
- When we need charts.
- When we need to prepare data for machine learning.
11. SQL Command to Pandas Statement Reference
This is the practical dictionary of SQL commands and their pandas equivalents. The SQL version is useful when data is inside a database. The pandas version is useful when data is already inside a DataFrame.
df. The second table/DataFrame is named
fees_df. The database connection is named connection.
11.1 Reading and selecting data
| SQL command | SQL example | pandas statement |
|---|---|---|
SELECT * |
SELECT * FROM students; |
df |
SELECT column |
SELECT name FROM students; |
df["name"] |
SELECT many columns |
SELECT name, marks FROM students; |
df[["name", "marks"]] |
AS |
SELECT marks AS final_marks FROM students; |
df.rename(columns={"marks": "final_marks"}) |
DISTINCT |
SELECT DISTINCT city FROM students; |
df["city"].drop_duplicates() |
COUNT DISTINCT |
SELECT COUNT(DISTINCT city) FROM students; |
df["city"].nunique() |
LIMIT |
SELECT * FROM students LIMIT 5; |
df.head(5) |
OFFSET |
SELECT * FROM students LIMIT 5 OFFSET 10; |
df.iloc[10:15] |
11.2 Filtering rows
| SQL command | SQL example | pandas statement |
|---|---|---|
WHERE = |
WHERE city = 'Varanasi' |
df[df["city"] == "Varanasi"] |
WHERE > |
WHERE marks > 70 |
df[df["marks"] > 70] |
WHERE >= |
WHERE marks >= 70 |
df[df["marks"] >= 70] |
WHERE < |
WHERE attendance < 75 |
df[df["attendance"] < 75] |
WHERE != |
WHERE city != 'Delhi' |
df[df["city"] != "Delhi"] |
AND |
WHERE marks >= 70 AND attendance >= 80 |
df[(df["marks"] >= 70) & (df["attendance"] >= 80)] |
OR |
WHERE city = 'Delhi' OR marks >= 90 |
df[(df["city"] == "Delhi") | (df["marks"] >= 90)] |
NOT |
WHERE NOT city = 'Delhi' |
df[~(df["city"] == "Delhi")] |
IN |
WHERE city IN ('Delhi', 'Lucknow') |
df[df["city"].isin(["Delhi", "Lucknow"])] |
NOT IN |
WHERE city NOT IN ('Delhi', 'Lucknow') |
df[~df["city"].isin(["Delhi", "Lucknow"])] |
BETWEEN |
WHERE marks BETWEEN 60 AND 90 |
df[df["marks"].between(60, 90)] |
LIKE |
WHERE name LIKE 'A%' |
df[df["name"].str.startswith("A", na=False)] |
LIKE contains |
WHERE name LIKE '%an%' |
df[df["name"].str.contains("an", case=False, na=False)] |
IS NULL |
WHERE marks IS NULL |
df[df["marks"].isna()] |
IS NOT NULL |
WHERE marks IS NOT NULL |
df[df["marks"].notna()] |
11.3 Sorting and calculated columns
| SQL command | SQL example | pandas statement |
|---|---|---|
ORDER BY ASC |
ORDER BY marks ASC |
df.sort_values("marks", ascending=True) |
ORDER BY DESC |
ORDER BY marks DESC |
df.sort_values("marks", ascending=False) |
ORDER BY many columns |
ORDER BY city ASC, marks DESC |
df.sort_values(["city", "marks"], ascending=[True, False]) |
calculated column |
SELECT marks + 5 AS bonus_marks FROM students; |
df.assign(bonus_marks=df["marks"] + 5) |
CASE WHEN |
CASE WHEN marks >= 40 THEN 'Pass' ELSE 'Fail' END |
df.assign(result=df["marks"].apply(lambda x: "Pass" if x >= 40 else "Fail")) |
CAST |
CAST(marks AS TEXT) |
df["marks"].astype(str) |
ROUND |
ROUND(marks, 2) |
df["marks"].round(2) |
11.4 Aggregation and grouping
| SQL command | SQL example | pandas statement |
|---|---|---|
COUNT(*) |
SELECT COUNT(*) FROM students; |
len(df) |
SUM() |
SELECT SUM(marks) FROM students; |
df["marks"].sum() |
AVG() |
SELECT AVG(marks) FROM students; |
df["marks"].mean() |
MIN() |
SELECT MIN(marks) FROM students; |
df["marks"].min() |
MAX() |
SELECT MAX(marks) FROM students; |
df["marks"].max() |
GROUP BY |
SELECT city, AVG(marks) FROM students GROUP BY city; |
df.groupby("city")["marks"].mean().reset_index() |
GROUP BY multiple aggregations |
SELECT city, COUNT(*), AVG(marks), MAX(marks) FROM students GROUP BY city; |
df.groupby("city").agg(total_students=("student_id", "count"), average_marks=("marks", "mean"), highest_marks=("marks", "max")).reset_index()
|
HAVING |
GROUP BY city HAVING AVG(marks) >= 70 |
df.groupby("city").filter(lambda g: g["marks"].mean() >= 70) |
11.5 Joins and set operations
| SQL command | SQL example | pandas statement |
|---|---|---|
INNER JOIN |
students INNER JOIN fees ON students.student_id = fees.student_id |
pd.merge(df, fees_df, on="student_id", how="inner") |
LEFT JOIN |
students LEFT JOIN fees ON students.student_id = fees.student_id |
pd.merge(df, fees_df, on="student_id", how="left") |
RIGHT JOIN |
students RIGHT JOIN fees ON students.student_id = fees.student_id |
pd.merge(df, fees_df, on="student_id", how="right") |
FULL OUTER JOIN |
students FULL OUTER JOIN fees ON students.student_id = fees.student_id |
pd.merge(df, fees_df, on="student_id", how="outer") |
CROSS JOIN |
students CROSS JOIN fees |
df.merge(fees_df, how="cross") |
UNION |
SELECT city FROM a UNION SELECT city FROM b; |
pd.concat([a["city"], b["city"]]).drop_duplicates().reset_index(drop=True) |
UNION ALL |
SELECT city FROM a UNION ALL SELECT city FROM b; |
pd.concat([a["city"], b["city"]], ignore_index=True) |
11.6 Insert, update, delete and table commands
| SQL command | SQL example | pandas statement |
|---|---|---|
CREATE TABLE |
CREATE TABLE students (...); |
df.to_sql("students", connection, if_exists="replace", index=False) |
INSERT INTO |
INSERT INTO students VALUES (...); |
pd.concat([df, pd.DataFrame([new_row])], ignore_index=True) |
INSERT many rows into SQL |
INSERT INTO students ... |
new_rows_df.to_sql("students", connection, if_exists="append", index=False) |
UPDATE |
UPDATE students SET marks = 100 WHERE name = 'Amit'; |
df.loc[df["name"] == "Amit", "marks"] = 100 |
DELETE |
DELETE FROM students WHERE marks < 40; |
df = df[df["marks"] >= 40] |
DROP TABLE |
DROP TABLE students; |
del df or remove the SQL table with
connection.execute("DROP TABLE students") |
ALTER TABLE ADD COLUMN |
ALTER TABLE students ADD COLUMN grade TEXT; |
df["grade"] = "" |
ALTER TABLE RENAME COLUMN |
ALTER TABLE students RENAME COLUMN marks TO final_marks; |
df = df.rename(columns={"marks": "final_marks"}) |
CREATE INDEX |
CREATE INDEX idx_city ON students(city); |
df = df.set_index("city") |
DROP INDEX |
DROP INDEX idx_city; |
df = df.reset_index() |
11.7 Subqueries, Common Table Expressions and window ideas
| SQL command | SQL example | pandas statement |
|---|---|---|
Subquery |
WHERE marks > (SELECT AVG(marks) FROM students) |
df[df["marks"] > df["marks"].mean()] |
WITH / CTE |
WITH top_students AS (...) SELECT * FROM top_students; |
top_students = df[df["marks"] >= 70] |
ROW_NUMBER() |
ROW_NUMBER() OVER (ORDER BY marks DESC) |
df.sort_values("marks", ascending=False).assign(row_number=lambda x: range(1, len(x) + 1))
|
RANK() |
RANK() OVER (ORDER BY marks DESC) |
df["marks"].rank(method="min", ascending=False) |
PARTITION BY |
AVG(marks) OVER (PARTITION BY city) |
df["city_average"] = df.groupby("city")["marks"].transform("mean") |
LAG() |
LAG(marks) OVER (ORDER BY student_id) |
df["previous_marks"] = df.sort_values("student_id")["marks"].shift(1) |
11.8 Running the same idea directly through SQL from pandas
Sometimes the best pandas statement is not a DataFrame operation. It is simply
pd.read_sql_query() with the SQL command inside it.
query = """
SELECT city, AVG(marks) AS average_marks
FROM students
GROUP BY city
HAVING AVG(marks) >= 70
ORDER BY average_marks DESC
"""
result_df = pd.read_sql_query(query, connection)
print(result_df)
12. Using SQL Query Result for Model Training
Now we will use SQL to pull the columns needed for training. Then pandas will prepare the data for the model.
11.1 Pull training data using SQL
query = """
SELECT
hours,
attendance,
marks
FROM students
"""
training_df = pd.read_sql_query(query, connection)
print(training_df)
11.2 Prepare input and output
X = training_df[["hours", "attendance"]]
y = training_df["marks"]
| Variable | Meaning |
|---|---|
X |
Input columns used by the model. |
y |
Target column that the model will learn to predict. |
11.3 Train-test split
X_train, X_test, y_train, y_test = train_test_split(
X,
y,
test_size=0.25,
random_state=42
)
11.4 Train Linear Regression model
model = LinearRegression()
model.fit(X_train, y_train)
11.5 Check score
score = model.score(X_test, y_test)
print("Model score:", score)
11.6 Make prediction
new_student = [[7, 92]]
prediction = model.predict(new_student)
print("Predicted marks:", prediction[0])
13. Saving SQL Results, DataFrames and Models
After querying and training, we may want to save the result in different forms.
12.1 Save SQL query result as CSV
query = """
SELECT name, city, marks
FROM students
WHERE marks >= 70
ORDER BY marks DESC
"""
top_students_df = pd.read_sql_query(query, connection)
top_students_df.to_csv("top_students.csv", index=False)
12.2 Save SQL query result back into another SQL table
top_students_df.to_sql(
"top_students",
connection,
if_exists="replace",
index=False
)
12.3 Save trained model
joblib.dump(model, "marks_model.pkl")
12.4 Load trained model
loaded_model = joblib.load("marks_model.pkl")
prediction = loaded_model.predict([[8, 95]])
print(prediction[0])
12.5 Close database connection
connection.close()
Closing the connection is a good habit. It tells Python that we are done using the database.
14. Complete Mini Project
This full project creates data, saves it to SQL, queries it, joins tables, trains a model, creates predictions and saves everything.
import sqlite3
import pandas as pd
import matplotlib.pyplot as plt
import joblib
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression
# -------------------------------------------------
# 1. CREATE DATAFRAMES
# -------------------------------------------------
students_data = {
"student_id": [1, 2, 3, 4, 5, 6, 7, 8],
"name": ["Amit", "Ravi", "Sita", "Meena", "Kabir", "Anu", "Farhan", "Pooja"],
"city": ["Varanasi", "Lucknow", "Varanasi", "Delhi", "Lucknow", "Delhi", "Varanasi", "Lucknow"],
"hours": [1, 2, 3, 4, 5, 6, 7, 8],
"attendance": [55, 60, 65, 70, 78, 85, 90, 95],
"marks": [35, 42, 50, 58, 70, 80, 88, 96]
}
fees_data = {
"student_id": [1, 2, 3, 4, 5, 6, 7, 8],
"fees_paid": [5000, 4500, 5000, 4000, 3000, 5000, 4500, 5000],
"scholarship": [0, 500, 0, 1000, 1500, 0, 500, 0]
}
students_df = pd.DataFrame(students_data)
fees_df = pd.DataFrame(fees_data)
print("Students DataFrame")
print(students_df)
print("Fees DataFrame")
print(fees_df)
# -------------------------------------------------
# 2. CREATE SQLITE DATABASE
# -------------------------------------------------
connection = sqlite3.connect("school.db")
students_df.to_sql(
"students",
connection,
if_exists="replace",
index=False
)
fees_df.to_sql(
"fees",
connection,
if_exists="replace",
index=False
)
print("Tables saved into SQLite database.")
# -------------------------------------------------
# 3. BASIC SQL QUERY
# -------------------------------------------------
query = """
SELECT *
FROM students
"""
all_students = pd.read_sql_query(query, connection)
print("All students from SQL")
print(all_students)
# -------------------------------------------------
# 4. FILTERING WITH SQL
# -------------------------------------------------
query = """
SELECT name, city, hours, attendance, marks
FROM students
WHERE marks >= 70
ORDER BY marks DESC
"""
top_students = pd.read_sql_query(query, connection)
print("Top students")
print(top_students)
# -------------------------------------------------
# 5. GROUPING WITH SQL
# -------------------------------------------------
query = """
SELECT
city,
COUNT(*) AS total_students,
AVG(marks) AS average_marks,
MAX(marks) AS highest_marks
FROM students
GROUP BY city
ORDER BY average_marks DESC
"""
city_summary = pd.read_sql_query(query, connection)
print("City summary")
print(city_summary)
# -------------------------------------------------
# 6. JOINING TWO TABLES
# -------------------------------------------------
query = """
SELECT
students.student_id,
students.name,
students.city,
students.hours,
students.attendance,
students.marks,
fees.fees_paid,
fees.scholarship
FROM students
INNER JOIN fees
ON students.student_id = fees.student_id
"""
joined_df = pd.read_sql_query(query, connection)
print("Joined data")
print(joined_df)
# -------------------------------------------------
# 7. TRAINING DATA FROM SQL
# -------------------------------------------------
query = """
SELECT
hours,
attendance,
marks
FROM students
"""
training_df = pd.read_sql_query(query, connection)
X = training_df[["hours", "attendance"]]
y = training_df["marks"]
X_train, X_test, y_train, y_test = train_test_split(
X,
y,
test_size=0.25,
random_state=42
)
model = LinearRegression()
model.fit(X_train, y_train)
score = model.score(X_test, y_test)
print("Model score:", score)
# -------------------------------------------------
# 8. PRESENTATION
# -------------------------------------------------
training_df["predicted_marks"] = model.predict(X)
print("Training data with predictions")
print(training_df)
plt.scatter(training_df["hours"], training_df["marks"], label="Actual Marks")
plt.plot(training_df["hours"], training_df["predicted_marks"], label="Predicted Marks")
plt.xlabel("Study Hours")
plt.ylabel("Marks")
plt.title("Actual vs Predicted Marks")
plt.legend()
plt.show()
# -------------------------------------------------
# 9. SAVE RESULTS
# -------------------------------------------------
top_students.to_csv("top_students.csv", index=False)
city_summary.to_csv("city_summary.csv", index=False)
joined_df.to_csv("joined_student_fees.csv", index=False)
training_df.to_csv("training_with_predictions.csv", index=False)
training_df.to_sql(
"training_with_predictions",
connection,
if_exists="replace",
index=False
)
joblib.dump(model, "marks_model.pkl")
print("CSV files, SQL table and model saved successfully.")
# -------------------------------------------------
# 10. CLOSE DATABASE
# -------------------------------------------------
connection.close()
print("Database connection closed.")
15. Important Features Explained
sqlite3.connect()
connection = sqlite3.connect("school.db")
Creates a database file or connects to an existing database file.
df.to_sql()
df.to_sql("table_name", connection, if_exists="replace", index=False)
Saves a pandas DataFrame as a SQL table.
pd.read_sql_query()
df = pd.read_sql_query(query, connection)
Runs a SQL query and returns the result as a pandas DataFrame.
Triple-quoted SQL string
query = """
SELECT name, marks
FROM students
WHERE marks >= 70
"""
Triple quotes allow us to write multi-line SQL queries clearly.
connection.close()
connection.close()
Closes the database connection after work is finished.
index=False
Prevents pandas from saving its automatic index as a separate column.
if_exists="replace"
Replaces old SQL table with a new one. Useful during practice.
if_exists="append"
Adds new rows to an existing SQL table.
16. Practice in Our Python Editor
Use the embedded Python editor below to test pandas and SQL examples from this lesson.
17. Practice Tasks
- Create a DataFrame named
products_df. - Add columns:
product_id,product_name,category,price,units_sold. - Create a SQLite database named
shop.db. - Save the DataFrame as a SQL table named
products. - Write a SQL query to select all products.
- Write a SQL query to find products where price is greater than 500.
- Write a SQL query to find total units sold by category.
- Write a SQL query to find average price by category.
- Bring the result into pandas using
pd.read_sql_query(). - Save the final result as
product_summary.csv.
Self Test
What does pd.read_sql_query() do?
It runs a SQL query and returns the result as a pandas DataFrame.
What does df.to_sql() do?
It saves a pandas DataFrame as a SQL table.
What is SQLite?
SQLite is a lightweight database stored in a single file.
What is the use of WHERE?
WHERE filters rows based on a condition.
What is the use of GROUP BY?
GROUP BY groups rows and helps calculate summaries such as average, count and sum.
What is the use of JOIN?
JOIN combines data from two or more tables using a common column.
Does SQL train the model?
No. SQL pulls and prepares the data. scikit-learn trains the model.
18. Final Summary
DataFrame
↓
SQLite database
↓
to_sql()
↓
SQL query
↓
read_sql_query()
↓
pandas DataFrame
↓
analysis, chart, training, saving