פייתון — דף עזר לראיון

אין תוצאה לחיפוש. נקה את החיפוש.

בסיס

הדפסה למסך
print("hello")
print("x =", x)        # מדפיס כמה דברים
print(f"x = {x}")      # f-string
קריאת קלט / הערה
# זו הערה
line = input()                 # קורא שורה כטקסט
nums = list(map(int, input().split()))  # שורת מספרים

משתנים וטיפוסים

משתנה — שומר ערך, בלי להגדיר טיפוס
x = 5
name = "Amir"
a, b = 1, 2        # שני ערכים בשורה
a, b = b, a        # החלפה
הטיפוסים הנפוצים
n = 5          # int  מספר שלם
f = 3.14       # float מספר עשרוני
s = "text"     # str  טקסט
ok = True      # bool  True / False
nothing = None # ריק (כמו null)

תנאים

תנאי — שים לב להזחה (רווחים), אין סוגריים מסולסלים
if x > 10:
    print("big")
elif x > 5:
    print("mid")
else:
    print("small")
חיבור תנאים — and / or / not (במקום && / || / !)
if x > 0 and x < 10:    # גם וגם   (כמו &&)
    ...
if x < 0 or x > 100:    # או     (כמו ||)
    ...
if not done:            # הפוך    (כמו !)
    ...
תנאי קצר בשורה אחת
sign = "+" if x >= 0 else "-"
# אם x >= 0 השם יקבל "+", אחרת "-"

לולאות

לולאה על מספרים
for i in range(5):       # 0,1,2,3,4
    print(i)
for i in range(2, 10, 2):  # מ-2 עד 10, בקפיצות 2
    ...
לולאה על אוסף
nums = ["a", "b", "c"]
for item in nums:
    print(item)          # a, אחר כך b, אחר כך c
enumerate — נותן גם את המיקום וגם את הערך
nums = ["a", "b", "c"]
for i, item in enumerate(nums):
    print(i, item)
# 0 a
# 1 b
# 2 c

כלומר: i הוא המיקום (0,1,2), item הוא הערך. חוסך ניהול מונה ידני.

while — הוספה והחסרה (בפייתון אין ++ או --)
x = 5
while x > 0:
    x -= 1     # מוריד 1   (במקום x--)
x += 1         # מוסיף 1   (במקום x++)

פונקציות

פונקציה — קטע קוד עם שם
def add(a, b=0):     # b ברירת מחדל = 0
    return a + b

add(2, 3)            # 5
add(2)               # 2
החזרת כמה ערכים
def stats(nums):
    return min(nums), max(nums)

lo, hi = stats([3, 1, 2])

רשימה (list)

אוסף מסודר של ערכים
a = [3, 1, 2]
a.append(4)       # [3,1,2,4]  הוספה בסוף
a.extend([5, 6])  # [3,1,2,4,5,6]  הוספת כמה ביחד
a.pop()           # מוציא את האחרון ומחזיר אותו
a[0]              # 3   ראשון
a[-1]             # אחרון
len(a)            # אורך
3 in a            # True   האם קיים?
שינוי ערך — רשימה ניתנת לשינוי (mutable)
a = [10, 20, 30]
a[1] = 99         # [10, 99, 30]  משנים לפי אינדקס
העתקה — y = x זה אותה רשימה! לעותק חדש צריך x[:]
x = [1, 2, 3]
y = x             # אותה רשימה! שינוי ב-y משנה גם את x
y.append(4)       # עכשיו x גם [1,2,3,4]

z = x[:]          # רשימה חדשה (עותק). שינוי ב-z לא נוגע ב-x
# גם list(x) או x.copy() עושים עותק
חיתוך (slice) — [התחלה:סוף:קפיצה]
a = [10, 20, 30, 40, 50]
a[1:3]            # [20, 30]   מאינדקס 1 עד 3 (לא כולל)
a[:2]             # [10, 20]   מההתחלה
a[2:]             # [30,40,50] עד הסוף
a[::2]            # [10,30,50] כל אחד שני (קפיצה 2)
a[0:4:2]          # [10, 30]   מ-0 עד 4, בקפיצות 2
a[::-1]           # [50,40,30,20,10]  הפוך

למה [::2] שימושי: לקחת רק אינדקסים זוגיים, או לדגום כל ערך שני.

סינון מהיר לרשימה חדשה
evens = [n for n in a if n % 2 == 0]  # רק הזוגיים

מילון (dict)

זוגות של מפתח וערך
d = {}
d["a"] = 1
d["a"]            # 1   שליפה
d.get("x", 0)     # 0   ערך אם המפתח לא קיים
"a" in d          # True   האם המפתח קיים?
del d["a"]        # מוחק את המפתח "a"
for k, v in d.items():
    print(k, v)   # מפתח וערך יחד
לקבל את כל המפתחות / הערכים כרשימה
d = {"a": 5, "b": 9}
list(d.keys())    # ["a", "b"]   רק המפתחות
list(d.values())  # [5, 9]       רק הערכים
לבדוק אם כל הערכים שווים למשהו
all(v == 0 for v in d.values())   # True אם כל הערכים 0
any(v > 0 for v in d.values())    # True אם לפחות אחד גדול מ-0
לספור הופעות (טריק נפוץ)
d[x] = d.get(x, 0) + 1   # מוסיף 1 לכל הופעה

סט (set)

אוסף בלי כפילויות, בדיקת קיום מהירה
s = set()
s.add(1)           # מוסיף ערך אחד
s.update([2, 3])   # מוסיף כמה ביחד
s.remove(2)        # מוחק (שגיאה אם לא קיים)
s.discard(9)       # מוחק בלי שגיאה אם לא קיים
1 in s             # True   בדיקה מהירה
s = {1, 2, 3}      # יצירה ישירה
len(set(nums)) != len(nums)   # יש כפילויות?
פעולות בין שני סטים
a = {1, 2, 3}
b = {2, 3, 4}
a | b      # {1,2,3,4}  איחוד (union)
a & b      # {2,3}      משותף (intersection)
a - b      # {1}        מה שיש ב-a ולא ב-b (difference)

שווה ערך: אפשר גם a.union(b), a.intersection(b), a.difference(b).

מחרוזת (str)

פעולות על טקסט (כל אחת עם התוצאה שלה)
s = "hello world"
s.split()              # ['hello', 'world']  פיצול לפי רווח
"a,b,c".split(",")     # ['a', 'b', 'c']    פיצול לפי תו
"-".join(["a","b"])    # 'a-b'   מחבר רשימה למחרוזת
"  hi  ".strip()       # 'hi'    מסיר רווחים מהקצוות
s.replace("l", "L")    # 'heLLo worLd'
s.upper()              # 'HELLO WORLD'
s.lower()              # 'hello world'
s.startswith("he")     # True
len(s)                 # 11   אורך
s[0]                   # 'h'  תו לפי אינדקס
s[::-1]                # 'dlrow olleh'  הפוך
"a" in s               # True   מכיל?
למיין מחרוזת לפי אותיות
t = "dbca"
sorted(t)              # ['a','b','c','d']  מחזיר רשימה
"".join(sorted(t))     # 'abcd'   מחזיר מחרוזת
"".join(sorted(t, reverse=True))  # 'dcba'  הפוך

שימושי לאנגרמות: שתי מילים הן אנגרמה אם "".join(sorted(a)) == "".join(sorted(b)).

מיון

ממיין רשימה — key קובע לפי מה
nums.sort()                 # מקטן לגדול
nums.sort(reverse=True)     # מגדול לקטן
words.sort(key=len)         # לפי אורך
people.sort(key=lambda p: p[1])  # לפי שדה

המרות וטריקים

המרות בין מבנים — עוטפים בשם של המבנה הרצוי
list("abc")        # ['a','b','c']   מחרוזת -> רשימה
list({1, 2, 3})    # [1, 2, 3]       סט -> רשימה
set([1, 1, 2])     # {1, 2}          רשימה -> סט (מוריד כפילויות)
"".join(["a","b"]) # 'ab'            רשימה -> מחרוזת
list(d.values())   # הערכים של מילון כרשימה
list(d.keys())     # המפתחות של מילון כרשימה

הרעיון: כדי להפוך משהו לרשימה עוטפים ב-list(...), לסט ב-set(...). עובר על האיברים ובונה מבנה חדש.

k המפתחות עם הערכים הכי גבוהים
d = {"a": 1, "b": 9, "c": 5}
sorted(d, key=d.get, reverse=True)[:2]   # ['b', 'c']

איך זה עובד: sorted(d) עובר על המפתחות, key=d.get ממיין כל מפתח לפי הערך שלו, reverse=True מהגבוה לנמוך, [:2] לוקח את 2 הראשונים. אפשר גם Counter(...).most_common(k) (קריא יותר).

מחלקה (class)

תבנית לאובייקט עם נתונים ופעולות
class Dog:
    def __init__(self, name):  # בנאי (self = האובייקט)
        self.name = name

    def bark(self):
        return self.name + " woof"

d = Dog("Rex")
d.bark()

כלים שמקצרים עבודה

Counter — סופר כמה פעמים כל ערך מופיע
from collections import Counter
c = Counter(nums)
c.most_common(2)   # שני הנפוצים ביותר
defaultdict — מילון שמתחיל לבד בערך ריק
from collections import defaultdict
g = defaultdict(list)
g[1].append(2)     # בלי שגיאה אם המפתח חדש
deque — תור / מחסנית מהירים
from collections import deque
q = deque()
q.append(1)        # מוסיף בסוף
q.popleft()        # מוציא מההתחלה (תור)
q.pop()            # מוציא מהסוף (מחסנית)
heapq — מוציא תמיד את הקטן ביותר
import heapq
h = []
heapq.heappush(h, 3)
heapq.heappop(h)   # הקטן ביותר

הקמת מסד מאפס (טרמינל)

הסדר המלא — מלמעלה למטה, פעם אחת
# 1. מתקינים את ספריית פייתון (psycopg2)
# 2. מתקינים ומפעילים שרת Postgres
# 3. מתחברים מהקוד (dbname=postgres)
# 4. יוצרים טבלה
# 5. מוסיפים שורה + commit
# 6. בודקים עם psql שהשורה נכנסה
1. התקנת ספריית psycopg2 (אם import psycopg2 נכשל)
python3 -m pip install psycopg2-binary

# אם יש שגיאת "externally-managed-environment":
python3 -m pip install psycopg2-binary --break-system-packages

כלומר: מתקין את החבילה שמאפשרת ל-import psycopg2 לעבוד. פעם אחת לכל מחשב.

2. התקנה והרצה של Postgres (Mac, עם Homebrew)
brew install postgresql@16
brew services start postgresql@16   # מפעיל את השרת ברקע

psql -l                             # מציג את כל המסדים שקיימים

שים לב: דורש שה-Homebrew מותקן. אם brew לא קיים — מתקינים מ-brew.sh. בלי הרצת השרת תקבל "Connection refused".

3. פרטי החיבור בברירת מחדל ב-Mac טרי
conn = psycopg2.connect(
    host="localhost",
    dbname="postgres",   # מסד שקיים תמיד
    user="amirch",       # שם המשתמש שלך ב-Mac
    password="",         # ריק בהתקנה טרייה
    port=5432,
)

כלומר: אין צורך ב-postgres/secret. המשתמש הוא שם המשתמש שלך, הסיסמה ריקה, והמסד postgres קיים מראש.

4. יצירת טבלה (בקוד פייתון, לפני ההוספה)
cur.execute("""
    CREATE TABLE IF NOT EXISTS users (
        id   SERIAL PRIMARY KEY,
        name TEXT NOT NULL,
        age  INT
    )
""")
conn.commit()

כלומר: בלי זה תקבל "relation users does not exist". IF NOT EXISTS = בטוח להריץ שוב ושוב. SERIAL = id אוטומטי.

סוגי עמודות נפוצים — לבחור לפי הצורך
SERIAL          # מספר רץ אוטומטי (מושלם ל-id)
INT             # מספר שלם
BIGINT          # מספר שלם גדול מאוד
NUMERIC(10, 2)  # עשרוני מדויק (טוב לכסף)
REAL            # עשרוני רגיל (לא מדויק)
TEXT            # טקסט בכל אורך (הכי פשוט)
VARCHAR(50)     # טקסט עד 50 תווים
BOOLEAN         # TRUE / FALSE
DATE            # תאריך בלבד (2026-06-29)
TIMESTAMP       # תאריך + שעה

בקיצור: מספרים → INT / NUMERIC, טקסט → TEXT, כן/לא → BOOLEAN, זמן → TIMESTAMP.

תוספות לעמודה (constraints) — דוגמה מלאה
CREATE TABLE products (
    id      SERIAL PRIMARY KEY,        # מפתח ראשי
    name    TEXT NOT NULL,             # חובה, לא יכול להיות ריק
    email   TEXT UNIQUE,               # ערך ייחודי (בלי כפילויות)
    price   NUMERIC(10, 2) DEFAULT 0,  # ערך ברירת מחדל
    user_id INT REFERENCES users(id)   # מפתח זר לטבלה אחרת
)

כלומר: אחרי הטיפוס אפשר להוסיף כללים — חובה (NOT NULL), ייחודי (UNIQUE), ברירת מחדל (DEFAULT), קישור לטבלה אחרת (REFERENCES).

5. מסד נפרד — רק אם ביקשו ממך (לא חובה)
createdb mydb        # יוצר מסד חדש בשם mydb
# ואז בקוד: dbname="mydb"

חשוב: ה-dbname בקוד חייב להיות זהה למסד שאתה פותח ב-psql, אחרת אתה מסתכל במקום אחר. אם לא ביקשו — תישאר על postgres.

6. לבדוק שהשורה נכנסה — ישירות במסד
psql postgres            # נכנס למסד postgres

SELECT * FROM users;     # מציג את השורות (חובה ; בסוף)
\dt                      # רשימת הטבלאות
\d users                 # מבנה הטבלה
\q                       # יציאה חזרה לטרמינל

כלומר: ככה רואים את הרשומות בעיניים בלי להוסיף print לקוד. כל הרצה של INSERT מוסיפה שורה חדשה (לא דורסת).

חיבור ל-Postgres

המבנה של כל קובץ: מתחברים פעם אחת בהתחלה, סוגרים פעם אחת בסוף, ובאמצע כל הפעולות
import psycopg2

# 1. מתחברים — פעם אחת, בהתחלה
conn = psycopg2.connect(
    host="localhost", dbname="mydb",
    user="postgres", password="secret", port=5432,
)
cur = conn.cursor()

# 2. כאן באות כל הפעולות (ראה למטה),
#    משתמשים שוב ושוב באותו cur

# 3. סוגרים — פעם אחת, בסוף
cur.close()
conn.close()
הכלל: קוראים (SELECT) → fetch. משנים (insert/update/delete) → commit
# cur כבר קיים מהשלב למעלה. כל פעולה היא שורת execute אחת:
cur.execute("SQL כאן", (value,))   # הערכים תמיד בסוגריים אחרי
קריאה — מביא שורות בחזרה (בלי commit)
cur.execute("SELECT id, name FROM users WHERE age > %s", (18,))
rows = cur.fetchall()        # רשימה: [(1,"Amir"), (2,"Dana")]
for r in rows:
    print(r[0], r[1])        # r[0]=id, r[1]=name

# שורה אחת בלבד:
cur.execute("SELECT name FROM users WHERE id = %s", (1,))
row = cur.fetchone()         # שורה אחת, או None אם אין

כלומר: השאילתה הראשונה מביאה את כל היוזרים שהגיל שלהם גדול מ-18. השנייה מביאה את השם של היוזר עם id = 1.

הוספה (INSERT) — אל תשכח commit אחרי
cur.execute("INSERT INTO users (name, age) VALUES (%s, %s)", ("Amir", 30))
conn.commit()                # חובה! בלי זה ההוספה לא נשמרת

כלומר: מוסיף יוזר חדש בשם Amir בגיל 30.

עדכון (UPDATE) — אל תשכח commit אחרי
cur.execute("UPDATE users SET age = %s WHERE id = %s", (31, 1))
conn.commit()

כלומר: מעדכן את היוזר עם id = 1 — מציב לו גיל 31.

מחיקה (DELETE) — אל תשכח commit אחרי
cur.execute("DELETE FROM users WHERE id = %s", (1,))
conn.commit()
print(cur.rowcount)          # כמה שורות הושפעו

כלומר: מוחק את היוזר עם id = 1.

חשוב: ערכים תמיד עם %s — לא בתוך הטקסט. סוגריים עם פסיק גם לערך אחד: (18,)
cur.execute("SELECT * FROM users WHERE name = %s", ("Amir",))   # נכון
# לא ככה: f"... WHERE name = {name}"   ← לא בטוח

כלומר: מביא את כל הנתונים של היוזר ששמו Amir.