הבלוג של ינון פרק

טיפים קצרים וחדשות למתכנתים

שברת קיבלת

08/03/2020

החלק הכי קשה בללמוד משהו חדש הוא המעבר מ"אני יודע לבנות לפי ההוראות" ל"אני יודע לכתוב את ההוראות", או היכולת לשלב כמה דברים שאנחנו יודעים לדבר חדש שלא הופיע בספר. דמיינו לדוגמא שאתם לא מכירים את השפה האנגלית כלל ואני מספר לכם שהמשפט I have a cat מתרגם ל"יש לי חתול", המשפט I have a dog מתרגם ל"יש לי כלב", חתול זה cat, כלב זה dog ותפוח זה apple. עכשיו אם תנסו להגיד "יש לי תפוח" באנגלית אני חושב שכולכם תטעו ותגידו I have a apple, כי מי בכלל חושב שאנגלית לא מסוגלים להגיד שתי אותיות ניקוד אחת אחרי השניה אז ממציאים n באמצע. זה פשוט כלל אחר.

ואותו דבר בתכנות - אם אתם לא יודעים פייתון בכלל אני יכול לספר לכם שהתוכנית הבאה מדפיסה על המסך את הטקסט hello ynon:

name = "ynon"
print("hello " + name)

ואספר לכם שהתוכנית הבאה מדפיסה על המסך את המספר 42:

x = 42
print(x)

סיכוי לא רע שבשביל להדפיס את הטקסט hello 42 תחליטו לכתוב את הקוד הבא:

x = 42
print("hello " + x)

שכמובן לא יעבוד, כי מי בכלל חושב שמסביב לפלוס חייבים לכתוב שני דברים מאותו סוג.

מה שיפה שכל טעות כזאת מקרבת אותנו עוד צעד להבנה של המערכת: כשפייתון צועק עליי שאני לא יכול לשים מסביב לפלוס שני דברים מסוגים שונים למדתי משהו חדש על פייתון ועל סוגי משתנים. גיליתי כלל חדש של השפה.

הדרך ללמוד משהו חדש לכן היא פשוטה, משעממת ועובדת - בונים משהו קיים לפי ההוראות, משנים קצת לפי מה שנראה לנו הגיוני מתוך כוונה לשבור את המערכת, ואם שברנו להסתכל על הטעות וללמוד ממנה כלל נוסף. תחזרו על זה מספיק פעמים ותוכלו גם אתם לכתוב את ההוראות, במקום רק לעקוב אחריהן.

הייתי רוצה להיות טבח

07/03/2020

בחיים לא שמעתי על טבח שקם בבוקר ואומר "היום אני הולך לנסות לבשל פסטה. אני אתחיל - אולי זה יהיה מוכן לארוחת צהריים, אולי לארוחת ערב, ואולי רק לשבוע הבא". וגם אין מצב כשהפסטה כבר על האש שהטבח יסתכל עליה בקטע של "טוב זה נראה שעוד 5 דקות היא תהיה מוכנה, אבל גם יש מצב שזה ייקח עוד שעתיים או עוד שבועיים, אי אפשר לדעת".

כשאתה מתיישב להכין פסטה יש לוח זמנים ברור מה הולך לקרות מתי. אתה יכול לפשל עם הפסטה, אבל אין מצב להסתכל על הסיר ולהתלבט מה הדבר הבא שצריך לעשות.

ואנחנו? איפה. בן אדם קם בבוקר לכתוב פיצ'ר למערכת, עוברות שעתיים ואין לך מושג אם הפיצ'ר הולך להיות מוכן עד הצהריים, עד הערב או עד שבוע הבא. ובשום שלב בתהליך (אפילו אחרי שהפיצ'ר כבר מוכן ועובד) אתה לא יודע אם עוד שניה לא יתגלה איזה באג שישלח אותך לעוד שבוע עבודה.

תסכול בצד - חוסר היכולת לקבוע לוחות זמנים לעבודה הוא חלק מובנה בעבודה של מתכנתים. או כמו שאומרים אצלנו "זה לא באג, זה פיצ'ר". עכשיו כדאי שנתחיל להתרגל ולבנות לעצמנו שיטות עבודה שמחבקות את חוסר הידיעה.

ידע חוצה שפות

06/03/2020

ביטויים רגולאריים יעבדו כמעט בלי שינוי בכל שפת תכנות שתגיעו אליה. גם כשתנסו לפתוח קובץ בכל שפת תכנות תמצאו את עצמכם מעבירים פרמטר בשם Open Mode שיכול לקבל תמיד את אותו סט של ערכים. הפקודה strftime של Python מקבלת מחרוזת שמייצגת פורמט תאריך ומורכבת מאחוזים ואותיות, וזהה לגמרי לזו של strftime של רובי וגם של C++, perl ושפות רבות נוספות.

מי שיודע לעבוד עם Promises ב JavaScript יקלוט מהר מאוד איך להשתמש ב asyncio ב Python ואפילו ב std::async של C++ (למרות שבינינו שום דבר ב C++ לא נקלט מהר מאוד).

אותו דבר לגבי עבודה עם REST ו GraphQL, כתיבת שאילתות SQL, פיענוח של קבצי XML, ואפילו Multi Threaded Programming. הרבה מאוד מהידע שלנו יכול להיות בעל ערך במעבר לשפה חדשה.

בהתלבטות אם כדאי ללמוד נושא מסוים, כדאי לקחת בחשבון את מספר שפות התכנות שנושא זה מופיע בהן בצורה כזו או אחרת. ככל שנשקיע באיסוף מיומנויות חוצות שפות כך זה הולך להשתלם ולהחזיר את ההשקעה ברווח גדול בעתיד.

יוניקוד כל הדרך ב Python2

05/03/2020

אחד הדברים שמבלבלים ב Python2 הוא שמחרוזות אינן Unicode כברירת מחדל. הדבר מייצר המון טעויות של מתכנתים עם המון הודעות שגיאה שונות ומשונות. הנה כמה דוגמאות ופיתרונות שלהן.

המשך קריאה

המכשול

04/03/2020

מה שמפריד בין אנשים שמצליחים להרים פרויקטים לאנשים שנתקעים הוא לא העובדה שהראשונים יודעים מה הם עושים ותמיד הכל הולך להם, אלא מה כל קבוצה עושה אל מול המכשול.

המכשול זה הקוד שכתבת בדיוק כמו בתיעוד אבל משום מה אצלך לא עובד.

זה הדבר המוזר הזה שאתה מנסה לעשות שלא מופיע בתיעוד ושנראה שאף אחד באינטרנט לא עשה קודם.

זה הגילוי שהספריה שרצית לבחור בה בעצם לא יכולה לעשות את הדבר הזה שרצית.

זו ההבנה שמה שנראה כמו יומיים עבודה הולך לקחת חודש במקרה הטוב.

בכל פרויקט יש מכשול והרבה פעמים יש יותר מאחד. המכשול זאת הנקודה בה אנשים מתייאשים, זה החודש הראשון בחדר כושר, או השנה הראשונה בעבודה כעצמאי. אבל המכשול הוא גם מה שהופך את הדבר שאתה מנסה לבנות לבעל ערך, והוא הסיבה שלא כולם עושים את הפרויקט הזה. והדרך היחידה להתמודד עם המכשול היא להגביר מהירות, להשקיע יותר שעות, להיכנס לעובי הקורה ולפתור את הבעיה בכלים שאפילו לא חשבת שיש לך.

התגברות על מכשולים ובניה מוצלחת של הפרויקטים שהתחלתם הם הדברים שלאורך זמן הופכים אתכם למתכנתים טובים יותר.

הקשר (context)

03/03/2020

הסיבה המרכזית שקשה לנו ללמוד וליישם דברים חדשים נקראת "הקשר" או באנגלית Context. בשביל להבין את זה צריך להיזכר רגע איך המוח שלנו עובד.

אפשר לדמיין את המוח בתור רשת של כבישים שמחברים בין אתרים שונים. האתרים הם הדברים שאנחנו יודעים למשל חתימה של פונקציה מסוימת בשפת תכנות או איך להשתמש בפקודת for; הכבישים הם ההזדמנויות השונות בהן השתמשנו באותו פריט ידע. ככל שאתר מסוים מחובר ביותר כבישים, כלומר ככל שזה משהו שאנחנו משתמשים בו לעתים יותר קרובות בחיים וביותר הקשרים, כך נזכור את זה טוב יותר. עם הזמן כבישים שלא נוסעים בהם נמחקים ואתרים הופכים ללא נגישים וגם ההיפך - ככל שאנחנו מגיעים לאותם אתרים בדרכים חדשות ונוצרים כבישים חדשים כך הזיכרון הופך יותר חי.

קל לראות את האנלוגיה הזאת בפעולה כשמנסים לזכור בעל פה מילה או משפט. אם תנסו לזכור בעל פה מילה בודדת בשפה זרה תראו שזה ממש קשה ואחרי שעתיים אתם שוכחים אותה. מה שמפתיע שדווקא כשמנסים לזכור בעל פה משפט או אפילו סיפור קצר, המילה הראשונה במשפט "מזכירה" לנו את המילים שבאות אחריה וכך קל לנו יותר לזכור.

באותו האופן כשיש לי רשת כבישים טובה סביב נושא שאני לא מכיר, יהיה לי ממש קל ללמוד את הנושא החדש הזה. בגלל זה מתכנתי Java מצליחים ללמוד יחסית מהר C# - ההתנהגות ממופה כמעט אחד לאחד בין השפות, ואפשר להשתמש מחדש באותה רשת כבישים ורק להלביש עליה עוד כמה אתרים.

לעומת זאת המעבר מתכנות Back End לתכנות Front End הוא כבר הרבה יותר מסובך. הכל חדש וצריך לבנות רשת כבישים חדשה סביב אינספור מושגים ורעיונות חדשים. זה פשוט לא דומה לשום דבר שאנחנו כבר מכירים.

מה עושים עם זה? קל- כדאי להבין שלימוד נושא חדש כרוך הרבה פעמים בבניית רשת כבישים חדשה במוח, וככל שנוסיף עוד הצטלבויות, פריטי מידע וקשרים בין הדברים שאנחנו לומדים כך נצליח לזכור אותם טוב יותר. לכן כדאי מאוד גם לקרוא, גם לראות הרצאות ביוטיוב, גם לכתוב קוד, גם לשמוע פודקסט, גם להעתיק קוד מאחרים ולשנות אותו, גם לשמוע רכילויות על האנשים מאחורי הטכנולוגיה ואפילו לחפש את התמונות שלהם ברשת. כמה שאתם יודעים יותר מ"המסביב" של הטכנולוגיה כך תבנו יותר חיבורים במוח לרעיונות החדשים ותוכלו לזכור אותם טוב יותר.

רידאקס הוקס

02/03/2020

לפני כמה שבועות הסברתי לאנשים בקורס React על Redux ועל כל הדברים המדליקים שאפשר לעשות איתה. ההתחלה היתה מלהיבה וכולם אפילו הצליחו לשרוד את הסיפור על ה Stores והפונקציה reducer. ואז הגענו לחבר את כל העסק הזה ל React ויכולתי לראות קבוצה שלמה של תלמידים מרוכזים נעלמת והופכת לאוסף של מבטים מיואשים. והאמת? אני די מבין אותם.

נניח שיש לי State של אפליקציה שנראה ככה:

const initialState = {
  home: [
    { id: 1, text: "buy stuff", done: false },
    { id: 2, text: "clean the kitchen", done: false },
    { id: 3, text: "cook dinner", done: true }
  ],
  work: [
    { id: 4, text: "prepare webinar text", done: true },
    { id: 5, text: "write daily post", done: false },
    { id: 6, text: "prepare slides for talk", done: false }
  ],
  hobbies: [{ id: 7, text: "write a cool tetris game", done: false }]
};

ואני רוצה לכתוב קומפוננטת ריאקט שתציג את כל המשימות בקבוצה מסוימת, עד לא מזמן הייתי צריך לכתוב קוד שנראה כך:

const TaskGroup = connect((state, ownProps) => ({
  tasks: state[ownProps.group],
  group: ownProps.group
}))(function TaskGroup({ tasks, group }) {
  return (
    <div>
      <h2>{group}</h2>
      <ul>
        {tasks.map(task => (
          <li>{task.text}</li>
        ))}
      </ul>
    </div>
  );
});

ואני כותב את זה על הלוח ובעצמי לא מבין למה דברים צריכים להיראות ככה, מאיפה כל הסוגריים האלה ומי יום אחד יצטרך לתחזק את הטירוף הזה. וניסיתי, באמת שניסיתי - הצעתי להם להוציא החוצה את הפוקנציה mapStateToProps לפונקציה נפרדת כמו שכולם עושים, או לעצום עיניים בזמן שכותבים את הקוד כמו שכולם עושים, אבל כלום לא עזר.

והנה בזמן שאני כותב את הפוסט הזה ומקטר יושבים אנשים ב react-redux ועושים עבודה. עבודה נפלאה, עבודה שעושה את העבודה שלי הרבה יותר קלה. בקיצור גם הם עברו ל React Hooks. עכשיו אנחנו כבר יכולים לוותר על connect ועל החתימה המביכה שלו ולכתוב קוד שנראה כך:

function TaskGroup({ group }) {
  const tasks = useSelector(state => state[group]);

  return (
    <div>
      <h2>{group}</h2>
      <ul>
        {tasks.map(task => (
          <li>{task.text}</li>
        ))}
      </ul>
    </div>
  );
}

הפקודה useSelector מושכת מידע מה State ומחזירה אותו, וחוסכת לנו את כל העבודה המעיקה עם connect. וכן יש גם useDispatch שמחזירה את הפונקציה dispatch. פרטים נוספים ודוגמאות בתיעוד https://react-redux.js.org/api/hooks.

פיתוח משחק צוללות ב React, TypeScript ו MobX. חלק 3.

01/03/2020

בימים האחרונים כתבנו לוגיקה של משחק צוללות בגישה מונחית עצמים ב TypeScript. היום הגיע הזמן להוסיף ממשק משתמש מבוסס React ו MobX. מה שיפה ב MobX הוא שאם בחרנו לבנות את הלוגיקה בגישה מונחית עצמים, התוספת של MobX היא כמעט לא מורגשת.

המשך קריאה

פיתוח משחק צוללות ב React, TypeScript ו MobX. חלק 1.

28/02/2020

לפני כמה ימים פרסמתי פה הקדמה על מובאקס בעזרת דוגמא קטנה של ניהול רשימת פריטים לביצוע. זה היה כיף אבל בחיים הרבה פעמים ככל שמפתחים דברים מורכבים יותר גם נתקלים בבעיות מורכבות יותר - ולכן חשבתי לקחת כאן יישום דוגמא קצת יותר גדול עם מואקס שאולי ייתן לנו נקודת מבט נוספת על הפריימוורק ותהליך העבודה איתה.

בשביל שיהיה מעניין אני מפרסם את המדריך הזה ב-3 חלקים (היום, מחר ומחרתיים). אתם מוזמנים לקחת כל יום את הקוד של אותו יום, להקליד אצלכם ולראות שעובד, וכמובן בסוף כל חלק יהיה גם תרגיל הרחבה למיטיבי לכת. אני מקווה שהמשחק הזה ייתן לכם הבנה טובה יותר של MobX וגם הצצה לפינות בעבודה איתו ועם TypeScript.

המשך קריאה