Python BackendHub – Telegram
Python BackendHub
7.51K subscribers
314 photos
46 videos
11 files
432 links
Learning python & Backend Engineering, with Mani!

Youtube: https://www.youtube.com/@GitOverHere
Github: https://github.com/ManiMozaffar
Linkedin: https://www.linkedin.com/in/manimozaffar

تبلیغات نداریم

Admin: @Mani_nikou
Download Telegram
Python BackendHub
یک سوالی برام مطرح شده که چند درصد برنامه نویسا کراول زدن، پس ممنون میشم بگین، تاحالا کراول زدین؟ (کراول = داده کاوی از یک سایت)
البته این pure python نیست مثالم اینه که شما خودتون implement کردین حالا چه با built in module ها چه لایبری های کمکی مثل aiohttp

ولی سوالم اینجاست
چه چیزی باعث شد که شما از اسکرپی استفاده کنید؟
و چه چیزی باعث شده که سمت اسکرپی نرید؟

@ManiFoldsPython
Forwarded from Microfrontend.ir
آموزش PostgreSQL

در اولین ویدیو و مقدمه پلی لیست آموزش PostgreSQL به بررسی تاریخچه و روند شکل گیری پستگرس پرداختیم. از پروژه مادر یعنی Ingres و سپس اضافه شدن امکانات object-relational از طریق پروژه Post-Ingres صحبت کردیم و چند اکستنشن مهم پستگرس یعنی PostGIS و Timescale صحبت کردیم.

Video: https://youtu.be/2f9RAkpQGj4


playlist: https://www.youtube.com/playlist?list=PLJ9zDGwhhsByAI0AbbJ4oUTziNsaffKnq
〰️〰️〰️〰️〰️〰️
© | @microfrontend_ir
7😍4
دیفالت کانفیگ postgresql برای ترافیک بالا مناسب نیست

و وقتی این کانفیگ رو کاستومایز میکنید متوجه میشین چقدر پرفومنس بهتر میشه
و البته بیشتر ریسورس مصرف میشه 🙂

میتونید کانفیگ مناسب اپلیکیشنتون رو از سایت زیر پیدا کنید. الگوریتم خوبی داره
https://pgtune.leopard.in.ua/

@ManiFoldsPython
👍22👏32
آپدیت جدید گیتهاب اومده, و من چقدر با این فیچر حال کردم :))
میخواستم ریپو عوض کنم باید پنج تا کلیک میکردم یا میخواستم یک issue تو یک ریپو دیگه رو ببینم

@ManiFoldsPython
👍9
Forwarded from Python BackendHub
من همیشه به یک چیزی اعتقاد دارم و آن، دید مهندسی است. از خصوصیات مفید و بزرگ دانشگاه خوب رفتنم، همین دید مهندسی است.

حالا این دید مهندسی یعنی چی؟

یعنی شما وقتی بدونید memory management چیست و GC چه کاری تو پایتون انجام می‌دهد، باعث می‌شود کدی که می‌نویسید، memory friendly‌تر باشد.

یا وقتی SQL بلدید و PostgreSQL هم بلدید، باعث می‌شود خیلی وقتا query بنویسید که به جای ۳ بار هیت، یک هیت به دیتابیس بزند. out of box ترش این است که اگر query که می‌زنید، read هست، چند تا read replication بسازید و horizentonal scaling انجام دهید تا سرعت query بهتر شود. اگر می‌بینید query که می‌زنید، مثلاً ۱۰ درصد ریزالت کل دیتابیستون است و حجیم است، از طرفی مثلاً ۲ تا column خیلی استفاده می‌شود توی آن query، آن وقت می‌توانید ترکیب آن دو تا column را ایندکس کنید تا پرفورمنس بهتری بگیرید. اما اگر ریزالت برگشتی ۷۰ درصد دیتابیستون باشد، آن موقع ایندکسها سربار دیتابیستون می‌شوند و نه تنها کمک نمی‌کنند بلکه سرعت شما را هم کاهش می‌دهند.

به این می‌گویند دید مهندسی. یعنی بدانید از چه چیزی کجا و به چه اندازه‌ای استفاده کنید.

همه اینها را گفتم تا برسم به این کتاب:
https://www.amazon.com/Designing-Data-Intensive-Applications-Reliable-Maintainable/dp/1449373321

این کتاب به شما یک دید مهندسی فوق‌العاده می‌دهد. تازه شروع کردم و می‌تونم بگم محشره ✌️
🔥13👍8👎1🥰1
اگه با postgresql نسخه ۱۴ به بالا کار میکنید این مقاله به احتمال خیلی زیاد به دردتون میخوره.

Cascade of doom: JIT, and how a Postgres update led to 70% failure on a critical national service

https://dev.to/xenatisch/cascade-of-doom-jit-and-how-a-postgres-update-led-to-70-failure-on-a-critical-national-service-3f2a

نویسنده هم ایرانیه
@ManiFoldsPython
🔥4👍1
Forwarded from Python BackendHub
یک نکته ای که اضافه کنم اینه که اگه انگلیسی بلد نباشین همیشه از دنیا چند پله عقب ترین
یعنی تا داک فست ترجمه نشده نمیتونید بخونید
تا آموزش K8s فارسی نیاد نمیتونید یاد بگیرین
تا آموزش داکر فارسی نیاد نمیتونید یاد بگیرین
تا Mojo داکش فارسی نشه یا اموزش نیاد نمیتونید یاد بگیرین..
هیچوقت doc string رو نمیتونید بخونید.

پس هرچقدر برنامه نویس خوبیم که بشید هرچند احتمالش کم, اما همیشه عقبین از دنیا.

@ManiFoldsPython
👍22👎2
من خودم از کلاس چهارم کلاس زبان رفتم. ۱ سال تخصصی زبان خوندم. ۳ سال هم تو دانشگاه به زبان انگلیسی درس خوندم پس تجربیاتم رو بهتون میگم:

اولا اشتباهی که تقریبا تو ۹۰درصد کلاس های زبان تهران(تا ۶ سال پیش که من اطلاع داشتم) میشد این بود که هنوز طرف دو کلمه نمیتونه حرف بزنه میان گرامر به خردش میدن‌😄 اگه میخواین زبان یاد بگیرین اصلا سمت گرامر و writing نرید. شما نیاز دارید اول زبان رو بفهمید. من تاسال ۵ام زبان انگلیسی خوندم یک گرامر خیلی ساده هم بلد نبودم.

کامل متوجه شدن اولین قدمه
دومین قدم صحبت کردنه
و سومین قدم خوندنه
چهارمین قدم گرامره
پنجمین نوشتن
ششمی فعال کردن ضمیر ناخودآگاهتون در برابر زبان انگلیسی (که مثلا بی بی سی روشنه و شما تو موبایلتون هستین بدون اینکه تمرکز کنید خبرنگار چی داره میگه متوجه شین چی داره میگه)

تو این پست نمیگنجه که بگم برای هر مرحله چیکار کردن ولی برای اولین مرحله:
۱. دیدن انیمیشن تا یک سطحی که ۹۰درصد متوجه شین. اشتباهه شما فیلم ببینید وقتی متوجه نمیشید چی دارن میگن. انیمیشن لغات راحت تری داره و راحت تر میتونید متوجه شید. انقدر ببینید که کامل متوجه شین
دومین قدم:‌دیدن فیلم و یوتیوبه. فیلمی که میبینید نباید تاریخی باشه. نباید لهجه خاصی داشته باشه(مثل بریتیش یا اسکاتیش یا استرالیایی).
اولش با ساب تایتل انگلیسی ببینید. بعدش ساب تایتل انگلیسی رو بردارین زمانی که ۹۰درصد متوجه شدید چی میگن. حالا گوشتون هم عادت میکنه.

و از همه مهم تر, هیچوقت از translate انگلیسی به فارسی استفاده نکنید. خیلی سمه. هیچوقت زبان یاد نمیگیرین شما‌اگه اینکارو کنید.
چون تو ضمیر ناخودآگاهتون همیشه قبل حرف زدن باید یک دور فارسی فکر کنید بعد تبدیلش کنید به انگلیسی
بعد انگلیسی صحبت کنید.

ولی اگه از دیکشنری انگلیسی به انگلیسی استفاده کنید هم چشمتون بیشتر عادت میکنه به کلمه های جدید تر و هم همیشه انگلیسی فکر میکنید و انگلیسی حرف میزنید.

@ManiFoldsPython
👍30
اگر زبان انگلیسی بلد نباشید، احتمال اینکه در برنامه‌نویسی پیشرفت کنید کم هست.

اگر هم زبان انگلیسی بلد باشید تضمینی برای این پیشرفت نیست، ولی حداقل به انبوهی از منابع آموزشی رایگان (در هر موضوعی، نه فقط برنامه‌نویسی) دسترسی پیدا میکنید.

از یاد گرفتن یک زبان دوم ضرر نمیکنید.

@DevTwitter | <Amirreza Gh/>
👍25
دو visualization platform که از پایتون تو سورس کدشون استفاده شده و کلی دیتابیس ساپورت میکنن:

این یک autogenerative AI داره میاره که شما مینویسید چی میخواین و query هم خودش مینویسه. 😁البته هنوز لانچ نشده.
https://superset.apache.org/

این یکی هم عالیه.
https://redash.io/


@ManiFoldsPython
👍3
تو لینکدین دیدم جالب بود
@ManifoldsPython
21👍5😁4
Forwarded from ‌BenDev
👍7
‌BenDev
Voice message
چقدر حقه این ویس 🙂
خیلی وقتا همه فکر میکنن چون صرفا یک چیز تو فریم ورکه پس یعنی درسته. پس یعنی استفاده ازش خوبه.
این مثال لایبری مدرن و غیر مدرن و قدیمی نمیشناسه. تو فست بخواین تو کوکی JWT توکن پاس بدید باید یکم کاستومایز کنید چون دیفالت تو هدر تعریف شده و تو پروژه های تمرینی سباستین هم دقیقا همینطوریه در صورتی که این اشتباهه (قبلا توضیح دادم چرا)

و همینطور تو جنگو رست فریم ورک هم همینطوره. در واقع DRY رو تبدیل به Don't respect yourself کرده که به قول امیربهادر میری تو views.py میبینی صد مدل view مختلف هست و ادم گیج میشه. SOLID کلا زیر سوال میره و بیزنس لاجیکو تکنولوژیو همه رو میکنه توهم دیگه

"The most dangerous phrase in human language is We've always done it this way "
- Grace Hopper

@ManiFoldsPython
👍125
Well said :)

@ManifoldsPython
👍3👏1
Parse, don't validate

فکر کنید یک دیتا کلس داریم

@dataclass
class Order:
id: UUID
customer: Customer
created_at: datetime
accepted_at: Optional[datetime]
paid_at: optional[datetime]
shipped_at: Optional[datetime]


میخوایم این سناریو هارو پیاده سازی کنیم
Order that is received -> Order that is accepted
Order that is accepted -> Order that is paid
Order that is paid -> Order that is shipped

یک تابعی داریم که این چنین کار میکنه:
def ship_order(order: Order) -> Order:
...

خب طبیعتا مشکلی که وجود میاد اینه که چه چیزی باعث میشه که ما به flow و جریان دیتا احترام بذاریم؟
Order that is received -> Order that is shipped
چطور جلوی این رو میگیریم؟‌باید هردفعه تو ship order کلی چک بنویسیم که ۱۰۰درصد خیالمون راحت باشه که عملیاتی که میشه داره درست انجام میشه. به این کار میگن validation

تازه این یک سناریو ساده بود. همین ولیدیشن باید برای همه توابع دیگه ای که نیاز داریم نوشته شه یعنی:
accept_order
return_order
update_order

تازه وقتی تو سورس کد میبینیم همچین چیزی رو نمیدونیم کی باید این تابع رو کال کنیم و ایا type safe هست یا نه؟ یعنی اگه من هر اوردری بدم بهم اوردر شیپ شده میده؟ از کجا میتونم ۱۰۰درصد خیالم راحت باشه اروری چیزی نمیخوره؟ از کجا میتونم بفهمم اوردی که برمیگرده ship شده هست؟ پس باید doc string رو بخونم و همینطور کد هم چک کنم! و این خیلی بده 🙂

حالا parse چیه؟ وقتی اوردر رو parse میکنید یعنی دارید آنالیز میکنید اوردر دقیقا تو چه state ای قرار داره

def ship_order(order: PaidOrder) -> ShippedOrder:
...

و تو کلس PaidOrder هم ۱۰۰درصد پارس میکنم که اوردر باید تو وضعیت paid باشه. این کاملا تایپ سیفه یعنی هر PaidOrder ای بهش بدم ShippedOrder به من میده. بدون اینکه کد کثیف و پر از ولیدیشن نوشته شه تو تابع! و البته برای درکشم نیازی به داک استرینگ و خوندن کد ندارم‌:)


مقاله کامل تر

@ManiFoldsPython
👍11👏3👌2
Python BackendHub
امروز با اختلاف بسییااااار فاحش یکی از سخت ترین مصاحبه های تکنیکالمو دادم. با شرکتی که 2 ماه پیش رزومه فرستاده بودم مصاحبه فنی گرفتم شرکت نسبتا بزرگ و پیشرفته ای هست. (اسم شرکت رو به دلایل شخصی نمیتونم بگم). 2 ساعت و 45 دقیقه مصاحبه طول کشید تماما فنی. اما…
یک سوال تو مصاحبه ای که روش ریپلای زدم پرسیده شده بود ازم جالب بود:

۱. تفاوت having و where تو sql . که خب سوال راحتیه.

۲. چرا تو سناریویی که از having استفاده میکنیم نمیتونیم از where استفاده کنیم؟ (دلیل فنی پشت implementation having یا بهتره بگم دلیل وجود سینتکس having )

که دومیو نمیدونستم چون واقعا کنجکاو نشده بودم تاحالا. و البته بعدش سرچ کردم فهمیدم. کلا بعد از اون مصاحبه معمولا از هرچیزی که استفاده میکنم روزانه سعی میکنم علتشو متوجه شم. و واقعا به باز شدن دیدم کمک کرده این موضوع

تو کامنتا جوابشو بگید
@ManiFoldsPython
👍8
Python BackendHub
یک سوال تو مصاحبه ای که روش ریپلای زدم پرسیده شده بود ازم جالب بود: ۱. تفاوت having و where تو sql . که خب سوال راحتیه. ۲. چرا تو سناریویی که از having استفاده میکنیم نمیتونیم از where استفاده کنیم؟ (دلیل فنی پشت implementation having یا بهتره بگم دلیل…
جواب جفت سوالو تو کامنت اشاره کردن
دلیلش فقط به خاطر ‍execution order و تایم لاینی هست که اجرا میشه. یعنی where میاد قبل از group by اجرا میشه برای همین نمیتونستیم هیچ فیلتری توی group by امون انجام بدیم. مثلا میخوایم بگیم sum فلان فیلد بیشتر از ۱۰۰ باشه. نمیتونستیم با این معماری و where . (البته میشه cte زد)
و مرسی از مهدی عزیز بابت اشتراک گذاری این پست:

Visualizing a SQL query

SQL statements are executed by the database system in several steps, including:
- Parsing the SQL statement and checking its validity
- Transforming the SQL into an internal representation, such as relational algebra
- Optimizing the internal representation and creating an execution plan that utilizes index information
- Executing the plan and returning the results


@ManiFoldsPython
👍12
Forwarded from Sadra Codes
بررسی جوانب پایتون ۳.۱۲

از این به بعد می‌تونید fstring های تودرتو بنویسید. مثلا:
phrase = f"Hello {f"{name}"}"
# Hello Sadra

بنظرم آنچنان کاربردی نیست و فهمیدنش در نگاه اول یکم سخته. شاید هایلایترها درکش رو راحت‌تر کنن در آینده ولی یه فیچر جدید که اضافه شده و خوشم اومد، multiline fstring هست که بهتون اجازه می‌ده، اف استرینگ رو در چند خط بنویسید و حسابی expandش کنید. تازه می‌تونید در بدنه‌اش، کامنت هم بنویسید:

phrase = f"Hello {
name # User.name
}"
# Hello Sadra

بهینه‌سازی سیستم Tokenization. پایتون یه ماژول tokenizer داره که ازش واسه آنالیز و پارس کردن کلمات و حروف ولید پایتون استفاده می‌کنه. به هر چانک حروف از استرینگ ورودی توکن میگن. اکثر تول‌های linting و formatting از این ماژول واسه فرمت و لینت کردن کد پایتون استفاده می‌کنن. تا نسخه ۳.۱۱، این ماژول به زبان پایتون بود. بدلیل اضافه شدن nested fstring و مولتی لاین fstring، مجبور شدن این ماژول رو بازنویسی کنن و با C نوشتنشن و از لحاظ زمان runtime، سرعتش به شدت رفته بالا. این باعث میشه تمام tool هایی که از tokenizer استفاده می‌کنن، سریع‌تر اون ماکروهاشون ران شن.

لایبرری distutils دیپریکت شده و دیگه توی standard library قرار نداره. از این لایبرری واسه نوشتن و توزیع کردن پکیج پایتون استفاده میشد که به دلیل سرعت پایین و محدودیت‌هایی که نسبت به پکیج setuptools داشت، ملت همیشه میرفتن سمت setuptools. حتی خود pip هم به setuptools وابسته هست. اگه venv بسازین، میبینید که بصورت دیفالت، setuptools نصبه. یه نکته که هست، setuptools جزو standard library نیست و درواقع از هسته distutils پایتون استفاده می‌کنه. از اونجا که distutilsی دیگه در کار نیست و pip نسخه‌های ۲۲.۱ به بالا دیگه وابستگی به setuptools نداره، عملا هیچ ابزار رسمی‌ای واسه توزیع پکیج پایتون هم نخواهیم داشت. این هم خوبه، هم بد.

pip (>= 22.1) does not require setuptools to be installed in the environment. setuptools-based (and distutils-based) packages can still be used with pip install, since pip will provide setuptools in the build environment it uses for building a package.

حالا یه اتفاق دیگه هم افتاده. اونم اینکه venv دیگه بخشی از پکیج setuptools نیست. تا امروز بود ولی دیگه نیس. حالا چیکار میشه کرد؟ خب distutils مستقل شده و شما می‌تونید خودتون setuptools رو pip install کنید و ازش استفاده کنید و واسه venv هم، virtualenv نصب کنید. دیگه کامند زیر کار نمیکنه:

python -m venv venv

بطور کلی، از این به بعد هر محیط venv که با virtualenv می‌سازید، در isolatedترین شکل ممکن قرار دارن و site-packageتون خالی خالیه. حتی wheel هم ندارید. فقط pip رو دارید.

از این به بعد می‌تونید تایپ هینت kwargs** رو کاستومایز کنید. من خودم همیشه انوتیت می‌کردم به typing.Any ولی از این به بعد می‌تونید TypedDict رو بهش انوتیت کنید:

from typing import TypedDict, Unpack

class Values(TypedDict):
name: str
age: int

def main(**kwargs: Unpack[Values]): ...

یه تایپ هینت جدید اومده که خیلی خوشم اومد، typing.override هست. این موقعی بدرد می‌خوره که می‌خواین تایپ هینت ست کنید واسه متدی که توی subclass قراره اوررایت شه. اگه تغییری توی superclass ایجاد شه و اسم اون متد توی سوپرکلس تغییر کنه، اگه یه سیستم type checking داشته باشین یه چیز مثل mypy، حتما خطا رو می‌گیره و بهتون نشون میده. این درحالیه که اگه کد رو اجرا کنید، ممکنه خطا نگیرید و اون متد هم override نشه.

from typing import override

class A:
def greet(): ...

class B(A):
@override
def greet(): ...

توی این مثال، اگه روزی برسه که اسم متد greet توی سوپرکلس تغییر کنه به greeting، حتما type checker ارور میده ولی اگه annotate نکرده باشید، اروری دریافت نمی‌کنید و صرفا اون logic درست کار نمی‌کنه.

تمام comprehensionهایی که در بدنه فانکشن‌ها هستن، از لحاظ سرعت اجرا بهینه‌تر شدن.

ارور مسیج‌ها هم بهینه و هوشمندتر شدن. اگه که بتونن، در محدوده شرایط وسیع‌تری، سلوشن می‌دن.

دوتا سینتکس جدید هم اضافه شده به پایتون. یکی type هست که واسه Type Alias استفاده میشه و دیگری هم Type Parameter هست که یه مدل جدید واسه تعریف فانکشن‌ها و کلس‌های جنریک پایتونه. شیوه استفاده ازشون به این شکله:

type name = str
type age = int

قبلا باید جنریک فانکشن رو اینجوری تعریف می‌کردیم:

def greet(name: List[str]): ...

ولی الان می‌نویسیم:

type T = List[str]

def greet[T](name: T): ...

این باعث میشه که پرینسیپل DRY آسیب نبینه.
👍9
بزرگ ترین تغییر ۳.۱۲ نسبت به ۳.۱۱ که بنظرم صدرا اشاره نکرد بهش PEP 684 بود

A Per-Interpreter GIL
که البته فعلا تو سطح پایتون نیست و python api نداره.


ولی این تغییر تو ۳.۱۳ خودشو خیلی بیشتر نشون میده. جایی که API python اش میاد. طبق PEP 554.
https://peps.python.org/pep-0554/
جایی که ما میتونیم حالا از این تغییراتی که تو ۳.۱۲ انجام شده و API پایتونیش تو ۳.۱۳ هست استفاده کنیم‌:)

اینکه چیه و چیکار میکنه تو این پست نمیگنجه. توصیه میکنم حتما این دو PEP رو وقت بذارین و بخونید که از بقیه جلوتر باشید تا وقتی ۳.۱۳ اومد بدونید چی باید یاد بگیرید 😁 فقط یک مقایسه میکنم بین sub Interpreter و مولتی پروسس

True Parallelism -> Multiprocess: YES | Subinterpreters: Potential
Isolation -> Multiprocess: HIGH | Subinterpreters: MEDIUM
Overhead -> Multiprocess: HIGH | Subinterpreters: LOW

و توی theory حداقل باید Subinterpreters یک مموری ایزوله و هندل CPU Bound task به صورت بهینه تر رو به ما بدن که باعث میشه پایتون با استفاده از این مفهوم جدید برای real-time processing و streaming data بسیار مناسب تر شه. چرا؟‌چون میتونید یک subinterpreter داشته باشید که دیتا رو بگیره و یک subinterpreter داشته باشید که دیتا رو پروسس کنه که این ایزوله سازی باعث استفاده بهتر و بهینه تر از ریسورستون میشه و latency رو هم کاهش میده

@ManiFoldsPython
👍8
<خرافاتی و دروغ هایی که برنامه نویس ها بهش باور دارن>


Falsehoods programmers believe about names
People's names do not change
People’s names have an order to them
My system will never have to deal with names from China
I can safely assume that this dictionary of bad words contains no people’s names in it
People have names
---------------------------------------------------
Falsehoods programmers believe about time
The time zone in which a program has to run will never change
The system clock will never be set to a time that is in the distant past or the far future
One minute on the system clock has exactly the same duration as one minute on any other clock
A time stamp of sufficient precision can safely be considered unique
The duration of one minute on the system clock would never be more than an hour
---------------------------------------------------
More falsehoods programmers believe about time
The local time offset (from UTC) will not change during office hours.
My software is only used internally/locally, so I don’t have to worry about timezones
I can easily maintain a timezone list myself
Time passes at the same speed on top of a mountain and at the bottom of a valley
---------------------------------------------------
Falsehoods programmers believe about time zones
Every day without DST changes is 86400 (60 * 60 * 24) seconds long
If you have two UTC timestamps it is possible to calculate how many seconds will be between them even if one of the timestamps are a year into the future
The time 23:59:60 is always invalid
---------------------------------------------------
Falsehoods programmers believe about geography
Places have only one official name
Place names follow the character rules of the language
Place names can be written with the exhaustive character set of a country
Places have only one official address
Street addresses contain street names
---------------------------------------------------
Falsehoods programmers believe about addresses
No buildings are numbered zero
A road will have a name
A single postcode will be larger than a single building
OK, but you don't get multiple postcodes per building
Addresses will have a reasonable number of characters — less than 100, say
---------------------------------------------------
Falsehoods programmers believe about maps
All coordinates are in “Latitude/Longitude”
The shortest path between two points is a straight line
All programmers agree on the ordering of latitude and longitude pairs

منبع
@ManiFoldsPython
👍3😁2
https://www.sequoiacap.com/article/sebastian-ramirez-spotlight/
مصاحبه (زندگی نامه) سباستین رامیرز رو چند ساعت پیش خوندم و واقعا WOW!

شخصا این نکاتو حداقل برداشت کردم:

۱. برای موفق نشدن دلایل خیلی بیشتری داشت تا موفق شدن، ولی جا نزد!
۲. نشون میده شما مدرک دانشگاه نداشته باشید دنیا به اخر نمیرسه. سباستین حتی دیپلم هم نداره!
۳. به برنامه نویسی به عنوان درامد زایی نگاه نمیکرد بلکه لذت میبرد.
۴. خلاقیت و ترکیب و استفاده از برنامه نویسی برای حل چالش های شخصیش
۵. پافشاری رو اهدافش

حتماا بخونید توصیه میشه
@ManiFoldsPython
👍18