Learn Python Coding
Learn Python through simple, practical examples and real coding ideas. Clear explanations, useful snippets, and hands-on learning for anyone starting or improving their programming skills. Admin: @HusseinSheikho || @Hussein_Sheikho
显示更多📈 Telegram 频道 Learn Python Coding 的分析概览
频道 Learn Python Coding (@pythonre) 英语 语言赛道中的 是活跃参与者。目前社区聚集了 40 123 名订阅者,在 技术与应用 类别中位列第 3 250,并在 印度 地区排名第 9 587 位。
📊 受众指标与增长动态
自 невідомо 创建以来,项目保持高速增长,吸引了 40 123 名订阅者。
根据 01 九月, 2026 的最新数据,频道保持稳定运转。过去 30 天订阅人数变化为 146,过去 24 小时变化为 9,整体触达仍然可观。
- 认证状态: 未认证
- 互动率 (ER): 平均受众互动率为 1.86%。内容发布后 24 小时内通常能获得 1.08% 的反应,占订阅者总量。
- 帖子覆盖: 每篇帖子平均可获得 748 次浏览,首日通常累积 435 次浏览。
- 互动与反馈: 受众积极参与,单帖平均反应数为 2。
- 主题关注点: 内容集中在 math, harvard, oxford, supervision, waybienad 等核心主题上。
📝 描述与内容策略
作者将该频道定位为表达主观观点的平台:
“Learn Python through simple, practical examples and real coding ideas. Clear explanations, useful snippets, and hands-on learning for anyone starting or improving their programming skills.
Admin: @HusseinSheikho || @Hussein_Sheikho”
凭借高频更新(最新数据采集于 02 九月, 2026),频道始终保持新鲜度与高覆盖。分析显示受众积极互动,使其成为 技术与应用 类别中的关键影响点。
def show_error(self, message):
self.thread.quit()
QMessageBox.critical(self, "Error", message)
class FileWorker(QObject):
progress = pyqtSignal(int)
finished = pyqtSignal()
error = pyqtSignal(str)
def __init__(self):
super().__init__()
self.files = []
def set_files(self, files):
self.files = files
def process(self):
try:
total = len(self.files)
for i, file in enumerate(self.files):
# Simulate processing
time.sleep(0.5)
# Check for cancellation
if QThread.currentThread().isInterruptionRequested():
break
# Update progress
self.progress.emit(int((i + 1) / total * 100))
self.finished.emit()
except Exception as e:
self.error.emit(str(e))
---
## 🔹 Best Practices
1. Always clean up threads - Use finished signals
2. Never update UI from worker threads - Use signals
3. Validate file operations - Check permissions/existence
4. Handle drag-and-drop properly - Check MIME types
5. Make dialogs modal/non-modal appropriately - exec_() vs show()
---
### 📌 What's Next?
In Part 4, we'll cover:
➡️ Database Integration (SQLite, PostgreSQL)
➡️ Data Visualization (Charts, Graphs)
➡️ Model-View-Controller Pattern
➡️ Advanced Widget Customization
#PyQt5 #ProfessionalDevelopment #PythonGUI 🚀
Practice Exercise:
1. Build a thumbnail generator with progress reporting
2. Create a JSON config editor with file monitoring
3. Implement a thread-safe logging system for background tasksclass DraggableList(QListWidget):
def __init__(self):
super().__init__()
self.setDragEnabled(True)
self.setAcceptDrops(True)
self.setDragDropMode(QAbstractItemView.InternalMove)
for i in range(5):
self.addItem(f"Item {i+1}")
def startDrag(self, supportedActions):
item = self.currentItem()
mime_data = QMimeData()
mime_data.setText(item.text())
drag = QDrag(self)
drag.setMimeData(mime_data)
drag.exec_(Qt.MoveAction)
---
## 🔹 Threading with QThread
### 1. Worker Thread Pattern
class Worker(QObject):
finished = pyqtSignal()
progress = pyqtSignal(int)
def run(self):
for i in range(1, 101):
time.sleep(0.1)
self.progress.emit(i)
self.finished.emit()
class MainWindow(QMainWindow):
def __init__(self):
super().__init__()
self.thread = QThread()
self.worker = Worker()
self.worker.moveToThread(self.thread)
self.thread.started.connect(self.worker.run)
self.worker.finished.connect(self.thread.quit)
self.worker.finished.connect(self.worker.deleteLater)
self.thread.finished.connect(self.thread.deleteLater)
self.worker.progress.connect(self.update_progress)
self.thread.start()
def update_progress(self, value):
print("Progress:", value)
### 2. Thread Pool for Concurrent Tasks
from PyQt5.QtCore import QRunnable, QThreadPool
class Task(QRunnable):
def __init__(self, task_id):
super().__init__()
self.task_id = task_id
def run(self):
print(f"Starting task {self.task_id}")
time.sleep(2)
print(f"Finished task {self.task_id}")
pool = QThreadPool.globalInstance()
for i in range(5):
pool.start(Task(i))
print("Max threads:", pool.maxThreadCount())
---
## 🔹 Practical Example: File Processor
class FileProcessor(QMainWindow):
def __init__(self):
super().__init__()
self.setup_ui()
self.setup_thread()
def setup_ui(self):
self.setWindowTitle("File Processor")
# Central Widget
widget = QWidget()
layout = QVBoxLayout()
# File Selection
self.file_list = QListWidget()
self.file_list.setSelectionMode(QAbstractItemView.MultiSelection)
add_btn = QPushButton("Add Files")
add_btn.clicked.connect(self.add_files)
# Processing Controls
self.progress = QProgressBar()
process_btn = QPushButton("Process Files")
process_btn.clicked.connect(self.process_files)
# Layout
layout.addWidget(QLabel("Files to Process:"))
layout.addWidget(self.file_list)
layout.addWidget(add_btn)
layout.addWidget(self.progress)
layout.addWidget(process_btn)
widget.setLayout(layout)
self.setCentralWidget(widget)
def setup_thread(self):
self.thread = QThread()
self.worker = FileWorker()
self.worker.moveToThread(self.thread)
self.thread.started.connect(self.worker.process)
self.worker.progress.connect(self.progress.setValue)
self.worker.finished.connect(self.on_processing_finished)
self.worker.error.connect(self.show_error)
def add_files(self):
files, _ = QFileDialog.getOpenFileNames(
self, "Select Files", "", "All Files (*)")
self.file_list.addItems(files)
def process_files(self):
if self.file_list.count() == 0:
QMessageBox.warning(self, "Warning", "No files selected!")
return
files = [self.file_list.item(i).text()
for i in range(self.file_list.count())]
self.worker.set_files(files)
self.thread.start()
def on_processing_finished(self):
self.thread.quit()
QMessageBox.information(self, "Done", "Processing completed!")from PyQt5.QtWidgets import (QFileDialog, QColorDialog,
QFontDialog, QInputDialog, QMessageBox)
# File Dialog
file_path, _ = QFileDialog.getOpenFileName(
self, "Open File", "", "Text Files (*.txt);;All Files (*)")
# Color Dialog
color = QColorDialog.getColor()
# Font Dialog
font, ok = QFontDialog.getFont()
# Input Dialog
text, ok = QInputDialog.getText(self, "Input", "Enter your name:")
# Message Box
reply = QMessageBox.question(
self, "Message", "Are you sure?",
QMessageBox.Yes | QMessageBox.No, QMessageBox.No)
### 2. Custom Dialog Classes
Create reusable dialog windows:
class LoginDialog(QDialog):
def __init__(self, parent=None):
super().__init__(parent)
self.setWindowTitle("Login")
self.username = QLineEdit()
self.password = QLineEdit()
self.password.setEchoMode(QLineEdit.Password)
buttons = QDialogButtonBox(
QDialogButtonBox.Ok | QDialogButtonBox.Cancel)
buttons.accepted.connect(self.accept)
buttons.rejected.connect(self.reject)
layout = QFormLayout()
layout.addRow("Username:", self.username)
layout.addRow("Password:", self.password)
layout.addRow(buttons)
self.setLayout(layout)
def get_credentials(self):
return (self.username.text(), self.password.text())
# Usage
dialog = LoginDialog()
if dialog.exec_():
username, password = dialog.get_credentials()
---
## 🔹 File System Operations
### 1. File and Directory Handling
from PyQt5.QtCore import QDir, QFile, QFileInfo
# Check file existence
file_info = QFileInfo("path/to/file")
if file_info.exists():
print("File size:", file_info.size())
# Directory operations
directory = QDir()
directory.mkdir("new_folder")
print("Current path:", directory.currentPath())
# File reading/writing
file = QFile("data.txt")
if file.open(QIODevice.ReadOnly | QIODevice.Text):
stream = QTextStream(file)
content = stream.readAll()
file.close()
### 2. Monitoring File Changes
from PyQt5.QtCore import QFileSystemWatcher
class FileMonitor(QObject):
def __init__(self):
super().__init__()
self.watcher = QFileSystemWatcher()
self.watcher.fileChanged.connect(self.on_file_changed)
def add_file(self, path):
self.watcher.addPath(path)
def on_file_changed(self, path):
print(f"File changed: {path}")
monitor = FileMonitor()
monitor.add_file("important_file.txt")
---
## 🔹 Drag and Drop
### 1. Enabling Drag-and-Drop
class DropArea(QLabel):
def __init__(self):
super().__init__("Drop files here")
self.setAcceptDrops(True)
self.setAlignment(Qt.AlignCenter)
self.setStyleSheet("border: 2px dashed #aaa;")
def dragEnterEvent(self, event):
if event.mimeData().hasUrls():
event.acceptProposedAction()
def dropEvent(self, event):
for url in event.mimeData().urls():
file_path = url.toLocalFile()
print("Dropped file:", file_path)class SettingsWindow(QDialog):
def __init__(self):
super().__init__()
self.setWindowTitle("Settings")
layout = QVBoxLayout()
layout.addWidget(QLabel("Application Settings"))
self.setLayout(layout)
# In main window:
def show_settings(self):
settings = SettingsWindow()
settings.exec_() # Modal dialog
# OR settings.show() for non-modal
### 2. Window Communication
# Main window with signal
class MainWindow(QMainWindow):
settings_changed = pyqtSignal(dict)
def open_settings(self):
dialog = SettingsDialog(self) # Pass parent
if dialog.exec_():
self.settings_changed.emit(dialog.get_settings())
# Settings dialog
class SettingsDialog(QDialog):
def __init__(self, parent=None):
super().__init__(parent)
# ... setup UI ...
def get_settings(self):
return {"theme": self.theme_combo.currentText()}
---
## 🔹 Model-View Architecture
### 1. QListView with StringListModel
model = QStringListModel()
model.setStringList(["Item 1", "Item 2", "Item 3"])
list_view = QListView()
list_view.setModel(model)
# Add items
model.insertRow(model.rowCount())
model.setData(model.index(model.rowCount()-1), "New Item")
### 2. Custom Table Model
class CustomTableModel(QAbstractTableModel):
def __init__(self, data):
super().__init__()
self._data = data
def rowCount(self, parent=None):
return len(self._data)
def columnCount(self, parent=None):
return len(self._data[0]) if self._data else 0
def data(self, index, role=Qt.DisplayRole):
if role == Qt.DisplayRole:
return str(self._data[index.row()][index.column()])
return None
# Usage
data = [[1, "Alice"], [2, "Bob"], [3, "Charlie"]]
model = CustomTableModel(data)
table = QTableView()
table.setModel(model)
---
## 🔹 Practical Example: Text Editor
class TextEditor(QMainWindow):
def __init__(self):
super().__init__()
self.setup_ui()
self.setup_menu()
def setup_ui(self):
self.text_edit = QTextEdit()
self.setCentralWidget(self.text_edit)
# Status bar
self.statusBar().showMessage("Ready")
# Toolbar
toolbar = self.addToolBar("Tools")
save_act = QAction(QIcon("save.png"), "Save", self)
save_act.triggered.connect(self.save_file)
toolbar.addAction(save_act)
def setup_menu(self):
menubar = self.menuBar()
# File menu
file_menu = menubar.addMenu("File")
open_act = QAction("Open", self)
open_act.triggered.connect(self.open_file)
file_menu.addAction(open_act)
# Edit menu
edit_menu = menubar.addMenu("Edit")
edit_menu.addAction("Copy", self.text_edit.copy)
edit_menu.addAction("Paste", self.text_edit.paste)
def open_file(self):
path, _ = QFileDialog.getOpenFileName()
if path:
with open(path, 'r') as f:
self.text_edit.setText(f.read())
def save_file(self):
path, _ = QFileDialog.getSaveFileName()
if path:
with open(path, 'w') as f:
f.write(self.text_edit.toPlainText())
---
## 🔹 Best Practices
1. Separate UI code from business logic
2. Use models for complex data views
3. Optimize performance for large datasets
4. Localize strings for internationalization
5. Document signals and public methods
---
### 📌 What's Next?
In Part 3, we'll cover:
➡️ Dialogs & Message Boxes
➡️ File System Operations
➡️ Drag & Drop
➡️ Threading with QThread
#PyQt5 #GUIPython #ProfessionalDevelopment 🚀
Practice Exercise:
1. Create a contacts app with tree view and detail form
2. Build a styled calculator with custom buttons
3. Implement a multi-window image viewer with thumbnailsfrom PyQt5.QtWidgets import QTabWidget, QTextEdit, QWidget
class TabDemo(QWidget):
def __init__(self):
super().__init__()
tabs = QTabWidget()
# Tab 1: Text Editor
tab1 = QWidget()
text_edit = QTextEdit()
tab1_layout = QVBoxLayout()
tab1_layout.addWidget(text_edit)
tab1.setLayout(tab1_layout)
# Tab 2: Settings
tab2 = QWidget()
tab2_layout = QVBoxLayout()
tab2_layout.addWidget(QLabel("Settings Panel"))
tab2.setLayout(tab2_layout)
tabs.addTab(tab1, "Editor")
tabs.addTab(tab2, "Settings")
main_layout = QVBoxLayout()
main_layout.addWidget(tabs)
self.setLayout(main_layout)
### 2. Tree Widget (QTreeWidget)
def setup_file_tree(self):
tree = QTreeWidget()
tree.setHeaderLabels(["Name", "Size", "Type"])
# Add parent items
root = QTreeWidgetItem(tree)
root.setText(0, "Project Root")
# Add children
for file in ["main.py", "config.ini", "README.md"]:
child = QTreeWidgetItem(root)
child.setText(0, file)
child.setText(1, "10 KB")
child.setText(2, "Python" if file.endswith(".py") else "Text")
tree.expandAll()
return tree
### 3. Table Widget (QTableWidget)
def setup_data_table(self):
table = QTableWidget(5, 3) # Rows, columns
table.setHorizontalHeaderLabels(["ID", "Name", "Status"])
sample_data = [
[101, "Product A", "Active"],
[102, "Product B", "Inactive"],
[103, "Product C", "Pending"]
]
for row, data in enumerate(sample_data):
for col, text in enumerate(data):
item = QTableWidgetItem(str(text))
table.setItem(row, col, item)
table.resizeColumnsToContents()
return table
---
## 🔹 Custom Signals & Slots
### 1. Creating Custom Signals
from PyQt5.QtCore import pyqtSignal, QObject
class Worker(QObject):
progress_changed = pyqtSignal(int)
task_completed = pyqtSignal(str)
def run_task(self):
for i in range(1, 101):
time.sleep(0.05)
self.progress_changed.emit(i)
self.task_completed.emit("Task finished!")
### 2. Advanced Signal-Slot Connections
# Multiple signals to single slot
button1.clicked.connect(self.handle_click)
button2.clicked.connect(self.handle_click)
# Signal with arguments
self.worker.progress_changed.connect(self.update_progress_bar)
# Lambda slots
button.clicked.connect(lambda: self.process_data(param1, param2))
# Slot decorator
@pyqtSlot()
def on_button_click(self):
print("Button clicked!")
---
## 🔹 Styling with Qt Style Sheets (QSS)
### 1. Basic Styling
app.setStyleSheet("""
QPushButton {
background-color: #4CAF50;
border: none;
color: white;
padding: 8px 16px;
font-size: 14px;
}
QPushButton:hover {
background-color: #45a049;
}
QLineEdit {
padding: 5px;
border: 1px solid #ccc;
border-radius: 3px;
}
""")
### 2. Advanced Selectors
/* Style only buttons in the toolbar */
QToolBar QPushButton {
min-width: 80px;
}
/* Style checked checkboxes differently */
QCheckBox:checked {
color: #0085FF;
}
/* Style odd/even table rows */
QTableView::item:alternate {
background: #f0f0f0;
}
### 3. Dynamic Style Changes
# Change style programmatically
button.setStyleSheet("""
QPushButton {
background-color: red;
font-weight: bold;
}
""")
# Reset to default
button.setStyleSheet("")
---from PyQt5.QtWidgets import (QApplication, QWidget, QVBoxLayout,
QLabel, QLineEdit, QPushButton)
class ConverterApp(QWidget):
def __init__(self):
super().__init__()
self.setWindowTitle("Temperature Converter")
self.setup_ui()
def setup_ui(self):
# Create widgets
self.celsius_input = QLineEdit()
self.fahrenheit_input = QLineEdit()
self.convert_btn = QPushButton("Convert")
self.result_label = QLabel("Enter temperature to convert")
# Set up layout
layout = QVBoxLayout()
layout.addWidget(QLabel("Celsius:"))
layout.addWidget(self.celsius_input)
layout.addWidget(QLabel("Fahrenheit:"))
layout.addWidget(self.fahrenheit_input)
layout.addWidget(self.convert_btn)
layout.addWidget(self.result_label)
# Connect button click
self.convert_btn.clicked.connect(self.convert)
self.setLayout(layout)
def convert(self):
try:
if self.celsius_input.text():
# Celsius to Fahrenheit
celsius = float(self.celsius_input.text())
fahrenheit = (celsius * 9/5) + 32
self.fahrenheit_input.setText(f"{fahrenheit:.2f}")
self.result_label.setText("Conversion complete!")
elif self.fahrenheit_input.text():
# Fahrenheit to Celsius
fahrenheit = float(self.fahrenheit_input.text())
celsius = (fahrenheit - 32) * 5/9
self.celsius_input.setText(f"{celsius:.2f}")
self.result_label.setText("Conversion complete!")
except ValueError:
self.result_label.setText("Please enter a valid number!")
if __name__ == "__main__":
app = QApplication([])
window = ConverterApp()
window.show()
app.exec_()
---
## 🔹 PyQt5 Designer Tool
Qt Designer lets you create UIs visually:
1. Launch Designer:
pyqt5-tools designer
2. Design your interface (saves as .ui file)
3. Convert to Python code:
pyuic5 input.ui -o output.py
Example Usage:
from PyQt5 import uic
class MyApp(QMainWindow):
def __init__(self):
super().__init__()
uic.loadUi('design.ui', self) # Load UI file
---
## 🔹 Event Handling Basics
PyQt5 uses signals and slots for interactivity:
# Connecting signals to slots
button.clicked.connect(self.on_button_click)
checkbox.stateChanged.connect(self.on_checkbox_change)
line_edit.textChanged.connect(self.on_text_change)
# Example slot methods
def on_button_click(self):
print("Button clicked!")
def on_checkbox_change(self, state):
print("Checkbox state:", state)
def on_text_change(self, text):
print("Text changed to:", text)
---
## 🔹 Best Practices for Beginners
1. Organize code in classes/methods
2. Use layouts instead of absolute positioning
3. Name widgets clearly (e.g., self.login_btn)
4. Separate UI code from business logic
5. Handle errors gracefully in event handlers
---
### 📌 What's Next?
In Part 2, we'll cover:
➡️ Advanced Widgets (Tables, Trees, Tabs)
➡️ Custom Signals
➡️ Styling with QSS
➡️ Multiple Windows
#PyQt5Tutorial #GUIPython #LearnToCode 🚀
Practice Exercise:
1. Create a simple calculator app
2. Build a text editor with save/load buttons
3. Make a color picker that changes window backgroundpip install PyQt5 PyQt5-tools
Verify Installation:
import PyQt5
print(PyQt5.__version__) # Should show version like 5.15.4
---
## 🔹 Your First PyQt5 App
Let's create a simple window:
import sys
from PyQt5.QtWidgets import QApplication, QLabel, QWidget
# 1. Create the application object
app = QApplication(sys.argv)
# 2. Create main window
window = QWidget()
window.setWindowTitle("My First App")
window.setGeometry(100, 100, 400, 200) # x, y, width, height
# 3. Add a label
label = QLabel("Hello PyQt5!", parent=window)
label.move(150, 80) # x, y position
# 4. Show the window
window.show()
# 5. Run the application
sys.exit(app.exec_())
Code Breakdown:
1. QApplication: Manages app control flow
2. QWidget: Base class for all UI objects
3. QLabel: Displays text/images
4. exec_(): Starts the event loop
---
## 🔹 Core PyQt5 Components
### 1. Main Window Types
| Class | Purpose |
|-------|---------|
| QWidget | Basic empty window |
| QMainWindow | With menu bar, status bar, toolbars |
| QDialog | Popup dialog windows |
### 2. Common Widgets
from PyQt5.QtWidgets import (
QPushButton, # Clickable button
QLineEdit, # Single-line text input
QTextEdit, # Multi-line text area
QCheckBox, # Toggle option
QRadioButton, # Exclusive choice
QComboBox, # Dropdown menu
QSlider # Value selector
)
### 3. Layout Managers
from PyQt5.QtWidgets import (
QVBoxLayout, # Vertical arrangement
QHBoxLayout, # Horizontal arrangement
QGridLayout # Grid arrangement
)
---
## 🔹 Creating a Functional App
Let's build a temperature converter:def function_name(parameters):
# block of code
return result
---
### 4. Creating a Simple Function
def greet():
print("Hello, welcome to Python functions!")
greet() # Calling the function
---
### 5. Function with Parameters
def greet_user(name):
print(f"Hello, {name}!")
greet_user("Hussein")
---
### 6. Function with Return Value
def add(a, b):
return a + b
result = add(10, 5)
print(result) # Output: 15
---
### 7. Positional vs Keyword Arguments
def student_info(name, age):
print(f"Name: {name}, Age: {age}")
student_info("Ali", 22) # Positional
student_info(age=22, name="Ali") # Keyword
---
### 8. Default Parameter Values
def greet(name="Guest"):
print(f"Hello, {name}!")
greet() # Output: Hello, Guest!
greet("Hussein") # Output: Hello, Hussein!
---
### 9. Variable Number of Arguments
#### \*args – Multiple positional arguments:
def sum_all(*numbers):
total = 0
for num in numbers:
total += num
return total
print(sum_all(1, 2, 3, 4)) # Output: 10
#### \*\*kwargs – Multiple keyword arguments:
def print_details(**info):
for key, value in info.items():
print(f"{key}: {value}")
print_details(name="Ali", age=24, country="Egypt")
---
### **10. Scope of Variables**
#### Local vs Global Variables
x = "global"
def func():
x = "local"
print(x)
func() # Output: local
print(x) # Output: global
Use global keyword if you want to modify a global variable inside a function.
---
### 11. Docstrings (Function Documentation)
def square(n):
"""Returns the square of a number."""
return n * n
print(square.__doc__) # Output: Returns the square of a number.
---
### 12. Best Practices
• Use descriptive names for functions
• Keep functions short and focused
• Avoid side effects unless needed
• Add docstrings for documentation
---
### Exercise
• Create a function that takes a list and returns the average
• Create a function that takes any number of scores and returns the highest
• Create a function with default arguments for greeting a user by name and language
---
#Python #Functions #CodingBasics #ModularProgramming #CodeReuse #PythonBeginners
https://t.me/DataScience4requests library and a free API like ip-api.com.
---
### Step-by-Step Code
import tkinter as tk
from tkinter import messagebox
import requests
# Function to fetch IP information
def track_ip():
ip = entry.get().strip()
if not ip:
messagebox.showwarning("Input Error", "Please enter an IP or domain.")
return
try:
url = f"http://ip-api.com/json/{ip}"
response = requests.get(url)
data = response.json()
if data["status"] == "fail":
messagebox.showerror("Error", data["message"])
return
# Show info
result_text.set(
f"IP: {data['query']}\n"
f"Country: {data['country']}\n"
f"Region: {data['regionName']}\n"
f"City: {data['city']}\n"
f"ZIP: {data['zip']}\n"
f"ISP: {data['isp']}\n"
f"Timezone: {data['timezone']}\n"
f"Latitude: {data['lat']}\n"
f"Longitude: {data['lon']}"
)
except Exception as e:
messagebox.showerror("Error", str(e))
# GUI Setup
app = tk.Tk()
app.title("IP Tracker")
app.geometry("400x400")
app.resizable(False, False)
# Widgets
tk.Label(app, text="Enter IP Address or Domain:", font=("Arial", 12)).pack(pady=10)
entry = tk.Entry(app, width=40, font=("Arial", 12))
entry.pack()
tk.Button(app, text="Track IP", command=track_ip, font=("Arial", 12)).pack(pady=10)
result_text = tk.StringVar()
result_label = tk.Label(app, textvariable=result_text, justify="left", font=("Courier", 10))
result_label.pack(pady=10)
app.mainloop()
---
### Requirements
Install the requests library if not already installed:
pip install requests
---
### Exercise
• Enhance the app to export the result to a .txt or .csv file
• Add a map preview using a web view or link to Google Maps
• Add dark mode toggle for the GUI
---
\#Python #Tkinter #IPTracker #Networking #GUI #DesktopApp
https://t.me/DataScience4class TrieNode:
def __init__(self):
self.children = {}
self.is_end_of_word = False
---
#### Basic Operations
Insert Word:
def insert(root, word):
node = root
for char in word:
if char not in node.children:
node.children[char] = TrieNode()
node = node.children[char]
node.is_end_of_word = True
Search Word:
def search(root, word):
node = root
for char in word:
if char not in node.children:
return False
node = node.children[char]
return node.is_end_of_word
---
### 4. Example Usage of Trie
root = TrieNode()
insert(root, "hello")
insert(root, "helium")
print(search(root, "hello")) # True
print(search(root, "hel")) # False (prefix only)
---
### 5. Advantages and Disadvantages
| Data Structure | Advantages | Disadvantages |
| -------------- | -------------------------------------- | ------------------------------- |
| Red-Black Tree | Balanced, efficient search and update | Complex implementation |
| Trie | Fast prefix search and auto-completion | Memory-heavy with many children |
---
### 6. Summary
* Red-Black Trees and AVL Trees both keep BSTs balanced but with different balancing rules
* Tries are specialized for string data, enabling efficient prefix operations
* Both structures are essential for advanced algorithms and systems
---
### 7. Exercise
• Implement basic Red-Black Tree insertion (research needed)
• Implement delete operation in Trie
• Use Trie to implement a simple autocomplete function
• Compare search time for BST vs Trie on string data sets
---
#DSA #RedBlackTree #Trie #AdvancedTrees #DataStructures #Python
https://t.me/DataScience4log(n) for efficient performance.
---
### 2. AVL Tree – Introduction
An AVL Tree is a self-balancing Binary Search Tree named after inventors Adelson-Velsky and Landis.
Properties:
• For every node, the balance factor (height of left subtree – height of right subtree) must be -1, 0, or +1
• Automatically re-balances after insertions and deletions
---
### 3. Balance Factor Calculation
balance = height(left subtree) - height(right subtree)
Cases:
• Balance Factor > 1 → Left-heavy
• Balance Factor < -1 → Right-heavy
---
### 4. Rotations in AVL Trees
To restore balance, AVL trees use rotations:
Single Rotations:
• Right Rotation (LL Case)
• Left Rotation (RR Case)
Double Rotations:
• Left-Right Rotation (LR Case)
• Right-Left Rotation (RL Case)
---
### 5. AVL Tree Node Structure
class Node:
def __init__(self, key):
self.key = key
self.left = None
self.right = None
self.height = 1
---
### 6. Helper Functions
def get_height(node):
if not node:
return 0
return node.height
def get_balance(node):
if not node:
return 0
return get_height(node.left) - get_height(node.right)
def right_rotate(z):
y = z.left
T3 = y.right
y.right = z
z.left = T3
z.height = 1 + max(get_height(z.left), get_height(z.right))
y.height = 1 + max(get_height(y.left), get_height(y.right))
return y
def left_rotate(z):
y = z.right
T2 = y.left
y.left = z
z.right = T2
z.height = 1 + max(get_height(z.left), get_height(z.right))
y.height = 1 + max(get_height(y.left), get_height(y.right))
return y
---
### 7. Insertion in AVL Tree
def insert(node, key):
if not node:
return Node(key)
if key < node.key:
node.left = insert(node.left, key)
elif key > node.key:
node.right = insert(node.right, key)
else:
return node # no duplicate keys
# Update height
node.height = 1 + max(get_height(node.left), get_height(node.right))
# Get balance factor
balance = get_balance(node)
# Balance the tree
# Case 1 - Left Left
if balance > 1 and key < node.left.key:
return right_rotate(node)
# Case 2 - Right Right
if balance < -1 and key > node.right.key:
return left_rotate(node)
# Case 3 - Left Right
if balance > 1 and key > node.left.key:
node.left = left_rotate(node.left)
return right_rotate(node)
# Case 4 - Right Left
if balance < -1 and key < node.right.key:
node.right = right_rotate(node.right)
return left_rotate(node)
return node
---
### 8. Example AVL Tree Construction
root = None
for val in [10, 20, 30, 40, 50, 25]:
root = insert(root, val)
After insertion, the AVL Tree balances itself using appropriate rotations.
---
### 9. Traversals
Use any standard traversal to see the output:
def inorder(root):
if root:
inorder(root.left)
print(root.key, end=" ")
inorder(root.right)
---
### 10. Summary
• AVL Trees ensure that BSTs stay balanced
• Balance is maintained using rotations after insertion
• Time complexity for all operations is O(log n)
• AVL Trees are ideal when frequent insertions and deletions are expected
---
### Exercise
• Build an AVL Tree from a set of values
• Add functions for insert, get_height, get_balance, and inorder
• Test insertions that trigger all four types of rotations
• Bonus: Implement AVL deletion (complex but possible)
---
#DSA #BalancedTree #BinarySearchTree #Python
https://t.me/DataScienceclass Node:
def __init__(self, key):
self.key = key
self.left = None
self.right = None
#### Insert Function:
def insert(root, key):
if root is None:
return Node(key)
if key < root.key:
root.left = insert(root.left, key)
else:
root.right = insert(root.right, key)
return root
#### Example Tree:
root = None
for val in [50, 30, 70, 20, 40, 60, 80]:
root = insert(root, val)
This creates:
50
/ \
30 70
/ \ / \
20 40 60 80
---
### 4. Searching in BST
def search(root, key):
if root is None or root.key == key:
return root
if key < root.key:
return search(root.left, key)
else:
return search(root.right, key)
---
### 5. Finding Minimum and Maximum
def find_min(root):
while root.left:
root = root.left
return root.key
def find_max(root):
while root.right:
root = root.right
return root.key
---
### 6. Deleting a Node in BST
There are 3 cases:
1. Node has no children
2. Node has one child
3. Node has two children
def delete(root, key):
if root is None:
return root
if key < root.key:
root.left = delete(root.left, key)
elif key > root.key:
root.right = delete(root.right, key)
else:
# Node with only one child or no child
if root.left is None:
return root.right
elif root.right is None:
return root.left
# Node with two children
temp = find_min_node(root.right)
root.key = temp.key
root.right = delete(root.right, temp.key)
return root
def find_min_node(node):
while node.left:
node = node.left
return node
---
### 7. Inorder Traversal of BST
Inorder traversal of a BST gives sorted order:
def inorder(root):
if root:
inorder(root.left)
print(root.key, end=" ")
inorder(root.right)
---
### 8. Time and Space Complexity Summary
| Operation | Best Case | Average Case | Worst Case |
| --------- | --------- | ------------ | ---------- |
| Search | O(log n) | O(log n) | O(n) |
| Insert | O(log n) | O(log n) | O(n) |
| Delete | O(log n) | O(log n) | O(n) |
*Worst case occurs when tree is skewed (e.g., inserting sorted data)*
---
### 9. Applications of BST
• Search engines
• Sorted maps and sets
• Auto-complete features
• Database indexing
• Tree-based dictionaries
---
### 10. Summary
• BST enforces ordering which helps efficient operations
• Insertion, search, and deletion rely on recursive logic
• Traversals help in data processing
• Performance degrades in unbalanced trees — next part will cover balanced trees
---
### Exercise
• Write code to insert, delete, and search in a BST.
• Traverse the BST in inorder, preorder, and postorder.
• Add a function to count number of nodes and leaf nodes.
• Try inserting sorted data and observe tree structure (hint: use print or drawing).
#DSA #DataStructures #Tree #Python
https://t.me/DataScience4class Node:
def __init__(self, data):
self.data = data
self.left = None
self.right = None
# Example
root = Node(1)
root.left = Node(2)
root.right = Node(3)
---
### 6. Tree Traversals
Tree traversal means visiting all the nodes of a tree in a specific order.
• Inorder (LNR)
• Preorder (NLR)
• Postorder (LRN)
• Level Order (BFS using queue)
#### Example – Inorder Traversal (Left → Root → Right):
def inorder(root):
if root:
inorder(root.left)
print(root.data, end=" ")
inorder(root.right)
---
### 7. Build a Simple Binary Tree and Traverse It
# Tree Structure:
# 1
# / \
# 2 3
# / \
# 4 5
root = Node(1)
root.left = Node(2)
root.right = Node(3)
root.left.left = Node(4)
root.left.right = Node(5)
print("Inorder Traversal:")
inorder(root) # Output: 4 2 5 1 3
---
### 8. Applications of Binary Trees
• Expression evaluation
• Search algorithms (Binary Search Trees)
• Priority queues (Heaps)
• Huffman encoding trees (data compression)
• Syntax trees in compilers
---
### 9. Key Characteristics
• Recursive nature makes tree problems suitable for recursion
• Not sequential – can't be represented with only arrays or lists
• Memory-efficient using pointers in linked structure
---
### 10. Summary
• Trees are hierarchical and non-linear
• Binary trees limit nodes to max 2 children
• Various types of binary trees serve different use cases
• Tree traversal is fundamental for solving tree problems
---
### Exercise
Create a class-based binary tree and implement:
• Inorder, Preorder, and Postorder traversals
• Function to count total nodes and leaf nodes
---
#DSA #BinaryTree #DataStructures #Python #TreeTraversal
https://t.me/DataScience4