Python Tak Segerak untuk Pembangun Ejen
Asas asyncio, async def, await, gelung peristiwa — model mental tak segerak.
Python Tak Segerak untuk Pembangun Ejen ialah pelajaran Ejen AI percuma di CoddyKit. Ini ialah pelajaran 1 daripada 4. Anda boleh membaca keseluruhan pelajaran di bawah secara percuma — kemudian berlatih secara praktikal dalam pelayar menggunakan penyunting kod terbina dalam dan tutor kecerdasan buatan 24/7. Pelajaran ini merupakan sebahagian daripada laluan pembelajaran Ejen AI, dan kemajuan anda disegerakkan merentas web serta aplikasi CoddyKit. Kursus Ejen AI merangkumi sejumlah 4 pelajaran.
Mengapa Tak Segerak untuk Ejen?
Ejen membuat banyak panggilan yang terikat I/O: API LLM, permintaan web dan pertanyaan pangkalan data. Kod segerak menunggu tanpa melakukan kerja semasa panggilan ini selesai. Kod tak segerak menjalankan kerja lain sepanjang tempoh menunggu itu, lalu meningkatkan daya pemprosesan dengan ketara.
Asas Tak Segerak: async def dan await
async def mengisytiharkan fungsi korutin. await menggantung pelaksanaan sehingga operasi yang ditunggu selesai, sekali gus membolehkan gelung peristiwa menjalankan korutin lain sementara itu.
import asyncio
async def fetch_data(source: str) -> str:
print(f'Starting fetch from {source}')
await asyncio.sleep(1) # Simulates a network call
print(f'Finished fetch from {source}')
return f'Data from {source}'
async def main():
# Sequential: takes 2 seconds total
result1 = await fetch_data('source-A')
result2 = await fetch_data('source-B')
print('Sequential results:', result1, result2)
asyncio.run(main())
# asyncio.run() starts the event loop and runs main()
# It is the entry point for async programsGelung Peristiwa
gelung peristiwa ialah teras asyncio. Ia mengurus baris gilir korutin dan panggilan balik I/O, lalu menjalankannya apabila sudah bersedia. Semua kod tak segerak berjalan dalam gelung peristiwa pada satu Thread sahaja.
import asyncio
async def task_a():
print('Task A: start')
await asyncio.sleep(2)
print('Task A: done')
async def task_b():
print('Task B: start')
await asyncio.sleep(1)
print('Task B: done')
async def main():
# asyncio.gather runs both tasks concurrently
# Total time: ~2 seconds (not 3)
await asyncio.gather(task_a(), task_b())
print('Both tasks complete')
# Expected output order:
# Task A: start
# Task B: start
# Task B: done <- after 1s
# Task A: done <- after 2s
# Both tasks complete
asyncio.run(main())Korutin berbanding Thread
Thread bersifat koperatif: ia menyerahkan kawalan secara jelas menggunakan await. Thread bersifat prapintas: OS boleh bertukar antara Thread pada bila-bila masa. Korutin lebih ringan, tidak menghadapi masalah GIL untuk I/O dan lebih mudah difahami.
import asyncio
import threading
import time
# Thread approach: multiple OS threads
def thread_worker(name):
print(f'Thread {name}: start')
time.sleep(1) # Blocks the thread
print(f'Thread {name}: done')
threads = [threading.Thread(target=thread_worker, args=(i,)) for i in range(3)]
for t in threads:
t.start()
for t in threads:
t.join()
print('---')
# Coroutine approach: single-threaded event loop
async def coro_worker(name):
print(f'Coro {name}: start')
await asyncio.sleep(1) # Suspends, does NOT block other coroutines
print(f'Coro {name}: done')
async def main():
await asyncio.gather(*[coro_worker(i) for i in range(3)])
asyncio.run(main())
# Both approaches run 3 tasks in ~1 second total, but coroutines use one threadTitik Masuk asyncio.run()
asyncio.run() mencipta gelung peristiwa baharu, menjalankan korutin yang diberikan sehingga selesai dan menutup gelung tersebut. Ini ialah titik masuk standard untuk program tak segerak dalam Python 3.7+.
import asyncio
async def agent_main():
print('Agent starting')
# All agent async work goes here
results = await asyncio.gather(
asyncio.sleep(0.1), # Simulated LLM call
asyncio.sleep(0.1), # Simulated DB query
)
print('Agent done')
return 'complete'
# Run the agent
result = asyncio.run(agent_main())
print('Result:', result)
# WRONG: calling asyncio.run() inside an already-running event loop
# In Jupyter notebooks, use: await agent_main() directly
# Or: nest_asyncio.apply() then asyncio.run()Kesilapan Lazim: Menyekat dalam Konteks Tak Segerak
Jangan sekali-kali memanggil fungsi yang menyekat (time.sleep, requests.get, I/O fail segerak) dalam kod tak segerak. Tindakan ini menyekat keseluruhan gelung peristiwa dan menghapuskan semua keserentakan.
import asyncio
import time
import httpx
# WRONG: blocks the event loop
async def bad_agent_step():
time.sleep(2) # Blocks all other coroutines
# requests.get(url) # Also blocks - do NOT use requests in async code
return 'done'
# RIGHT: use async equivalents
async def good_agent_step():
await asyncio.sleep(2) # Suspends, other coroutines can run
async with httpx.AsyncClient() as client:
response = await client.get('https://api.example.com/data')
return response.text
# For CPU-intensive work: use run_in_executor
import concurrent.futures
async def cpu_intensive_step(data: str):
loop = asyncio.get_event_loop()
with concurrent.futures.ProcessPoolExecutor() as pool:
result = await loop.run_in_executor(pool, expensive_cpu_fn, data)
return result
def expensive_cpu_fn(data):
# CPU-bound work runs in separate process
return data.upper()
print('Blocking vs non-blocking patterns demonstrated')Terlupa await: Pepijat Senyap
Jika await terlupa, ralat tidak akan dicetuskan — sebaliknya, objek korutin dikembalikan dan bukannya hasil. Ini ialah pepijat senyap yang menyebabkan ralat susulan atau hasil kosong.
import asyncio
async def get_answer() -> str:
await asyncio.sleep(0.1)
return 'The answer is 42'
async def bad_call():
result = get_answer() # WRONG: forgot await
print(type(result)) # <class 'coroutine'> - not a string!
# Using result as a string here causes AttributeError or wrong behavior
return result
async def good_call():
result = await get_answer() # CORRECT
print(type(result)) # <class 'str'>
return result
async def main():
bad = await bad_call()
print('Bad result:', bad) # coroutine object, not the string
good = await good_call()
print('Good result:', good) # 'The answer is 42'
# Clean up the uncollected coroutine
if asyncio.iscoroutine(bad):
bad.close()
asyncio.run(main())Masalah Gelung Peristiwa Bersarang
Memanggil asyncio.run() di dalam gelung peristiwa yang sedang berjalan (contohnya, Jupyter atau FastAPI) akan mencetuskan RuntimeError. Penyelesaiannya: gunakan await secara terus atau gunakan nest_asyncio untuk buku nota.
import asyncio
async def my_agent_coroutine():
await asyncio.sleep(0.1)
return 'done'
# In FastAPI or other async frameworks, the event loop is already running
# Use await directly in async endpoints:
async def fastapi_endpoint():
# WRONG inside async context:
# result = asyncio.run(my_agent_coroutine()) # RuntimeError!
# CORRECT: just await
result = await my_agent_coroutine()
return result
# In Jupyter notebooks: install nest_asyncio
# import nest_asyncio
# nest_asyncio.apply()
# Then asyncio.run() works
# Detect if running in event loop:
def run_agent(coro):
try:
loop = asyncio.get_running_loop()
# Already in async context
import concurrent.futures
with concurrent.futures.ThreadPoolExecutor() as pool:
future = pool.submit(asyncio.run, coro)
return future.result()
except RuntimeError:
# No running loop
return asyncio.run(coro)
print('Nested event loop solution defined')asyncio.create_task
Gunakan asyncio.create_task() untuk menjadualkan korutin supaya berjalan tanpa menunggunya dengan serta-merta. Dengan cara ini, anda boleh memulakan beberapa tugasan dan menunggu penyelesaiannya kemudian.
import asyncio
async def background_job(job_id: int) -> str:
await asyncio.sleep(0.5)
return f'Job {job_id} completed'
async def main():
# Start all tasks without waiting
task1 = asyncio.create_task(background_job(1))
task2 = asyncio.create_task(background_job(2))
task3 = asyncio.create_task(background_job(3))
# Do other work while tasks run
print('Tasks started, doing other work...')
await asyncio.sleep(0.1)
print('Other work done')
# Now wait for all tasks
results = await asyncio.gather(task1, task2, task3)
print('All results:', results)
# Or wait for the first to complete
task_a = asyncio.create_task(background_job(4))
task_b = asyncio.create_task(background_job(5))
done, pending = await asyncio.wait([task_a, task_b], return_when=asyncio.FIRST_COMPLETED)
for t in pending:
t.cancel() # Cancel remaining tasks
print('First result:', done.pop().result())
asyncio.run(main())Pengurus Konteks Tak Segerak
Banyak pustaka tak segerak menggunakan pengurus konteks tak segerak dengan async with. Ini memastikan penyediaan dan pengemasan sambungan serta sumber dilakukan dengan betul dalam kod tak segerak.
import asyncio
import httpx
async def fetch_multiple_urls(urls: list) -> list:
# async with ensures the client is properly closed
async with httpx.AsyncClient(timeout=10.0) as client:
# Fetch all URLs concurrently
tasks = [client.get(url) for url in urls]
responses = await asyncio.gather(*tasks, return_exceptions=True)
results = []
for url, response in zip(urls, responses):
if isinstance(response, Exception):
results.append({'url': url, 'error': str(response)})
else:
results.append({'url': url, 'status': response.status_code})
return results
# Async generators for streaming
async def stream_agent_events():
events = ['thinking', 'searching', 'generating', 'done']
for event in events:
await asyncio.sleep(0.2) # Simulate event arrival
yield event
async def consume_stream():
async for event in stream_agent_events():
print(f'Event: {event}')
asyncio.run(consume_stream())Pengendalian Ralat dalam Kod Tak Segerak
Gunakan asyncio.gather(..., return_exceptions=True) untuk menangkap kegagalan tugasan secara individu tanpa menghentikan keseluruhan kelompok. Periksa setiap hasil untuk jenis pengecualian.
import asyncio
async def might_fail(task_id: int) -> str:
await asyncio.sleep(0.1)
if task_id == 2:
raise ValueError(f'Task {task_id} failed')
return f'Task {task_id} succeeded'
async def robust_gather():
tasks = [might_fail(i) for i in range(1, 5)]
# return_exceptions=True: exceptions are returned as values, not raised
results = await asyncio.gather(*tasks, return_exceptions=True)
successes = []
failures = []
for i, result in enumerate(results):
if isinstance(result, Exception):
failures.append({'task': i + 1, 'error': str(result)})
else:
successes.append(result)
print(f'Succeeded: {len(successes)}, Failed: {len(failures)}')
print('Failures:', failures)
return successes, failures
asyncio.run(robust_gather())Semakan Pengetahuan: Python Tak Segerak
Uji pemahaman anda tentang Python tak segerak untuk pembangunan ejen.
Ringkasan Python Tak Segerak
Peraturan utama Python tak segerak untuk pembangun ejen: gunakan async def/await untuk semua operasi yang terikat I/O; jangan sekali-kali memanggil fungsi yang menyekat dalam konteks tak segerak; gunakan asyncio.gather() untuk pelaksanaan selari; gunakan return_exceptions=True untuk panggilan selari yang toleran terhadap kegagalan; gunakan async with untuk pengurusan sumber; jalankan kerja yang intensif CPU dalam pelaksana himpunan proses.
Pelajari Ejen AI dengan tutor kecerdasan buatan — percuma
Tulis dan jalankan kod sebenar dalam pelayar anda, dapatkan bantuan segera daripada tutor kecerdasan buatan yang tersedia 24/7, dan sambung semula dari tempat anda berhenti di web atau dalam aplikasi.
- Kursus
- 60
- Pelajaran
- 239
Soalan Lazim
Adakah pelajaran “Python Tak Segerak untuk Pembangun Ejen” percuma?
Ya — teks penuh “Python Tak Segerak untuk Pembangun Ejen” boleh dibaca secara percuma di web ini. Untuk berlatih secara interaktif menggunakan penyunting kod terbina dalam dan tutor kecerdasan buatan 24/7, serta membuka kunci baki kursus Ejen AI, tingkat taraf kepada CoddyKit PRO. Kursus Ejen AI merangkumi sejumlah 4 pelajaran.
Apakah yang akan saya pelajari dalam “Python Tak Segerak untuk Pembangun Ejen”?
Asas asyncio, async def, await, gelung peristiwa — model mental tak segerak. Anda berlatih Ejen AI menggunakan kod praktikal yang dijalankan terus dalam pelayar, manakala tutor kecerdasan buatan 24/7 menjawab soalan anda semasa anda mengikuti pelajaran.
Adakah saya memerlukan pengalaman untuk memulakan Ejen AI?
Tiada pengalaman terdahulu diperlukan. Pembelajaran Ejen AI di CoddyKit disusun untuk pelajar daripada peringkat pemula hingga lanjutan, jadi anda boleh bermula di sini atau dari awal dan belajar mengikut kadar anda sendiri. Ini ialah pelajaran 1 daripada 4.
Berapa lamakah pelajaran “Python Tak Segerak untuk Pembangun Ejen” diambil?
Kebanyakan pelajaran CoddyKit mengambil masa kira-kira 5–10 minit. Setiap pelajaran ringkas dan interaktif, jadi anda boleh membuat kemajuan secara berterusan dan menyambung tepat dari tempat anda berhenti di web atau aplikasi.
Bolehkah saya menulis dan menjalankan kod dalam pelajaran Ejen AI ini?
Ya. Setiap pelajaran Ejen AI menyertakan penyunting kod terbina dalam, jadi anda boleh menulis dan menjalankan kod sebenar terus dalam pelayar serta menerima maklum balas kecerdasan buatan serta-merta — tanpa memerlukan persediaan setempat.
Semua pelajaran dalam kursus ini
- Python Tak Segerak untuk Pembangun Ejen
- Baris Gilir Peristiwa dan Broker Mesej
- Pelaksanaan Alat Selari Tanpa Sekatan
- Rangka Kerja Ejen Tak Segerak: LangChain dan Lain-lain