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

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

להבין או לפתור

03/12/2020

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

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

ועדיין כשמסתכלים קדימה על הקריירה שלך ועל איכות הקוד במערכת קל לראות שההתעקשות לכתוב רק קוד שאני מבין היא תמיד הבחירה המשתלמת. אולי לא משתלמת מבחינת Product (אין לי מושג מה לוחות הזמנים שלהם) אלא הכי משתלמת לעתיד הקריירה שלך.

חמש דקות על סיבוכיות

02/12/2020

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

וזה עבד, לפחות עד שעליתי לפרודקשן.

המשך קריאה

סוד התוכניות הנעלמות

01/12/2020

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

המשך קריאה

איך להוסיף כפתור Instant View לקישורי טלגרם שאתם משתפים

30/11/2020

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

המשך קריאה

ירח דבש

29/11/2020

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

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

  1. כל עוד כל פעם שאתם נתקעים יש תשובה מהירה ב Stack Overflow - אתם עדיין בירח הדבש

  2. כל עוד המערכת שלכם עובדת בלי ששברתם את הראש על שיפורי ביצועים - אתם עדיין בירח הדבש

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

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

למה split מחזיר אלמנטים ריקים כשיש כפילויות?

28/11/2020

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

>>> 'one two three'.split(' ')
['one', 'two', 'three']

מעניין לשים לב מה קורה כשתו ההפרדה מופיע יותר מפעם אחת ברצף:

>>> 'one   two   three'.split(' ')
['one', '', '', 'two', '', '', 'three']

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

>>> 'one    two   three'.split(None)
['one', 'two', 'three']
>>> 'one    two   three'.split()
['one', 'two', 'three']

ההתנהגות מתבהרת כשאנחנו נזכרים בפונקציה join, שהיא ההיפך של split. פונקציית join של מחרוזת מקבלת רשימה ומדביקה אותה חזרה תוך שימוש במחרוזת המקורית כתו הפרדה:

>>> '-'.join(['yo', 'dog'])
'yo-dog'

בזכות התאים הריקים ברשימה ש split מחזירה, אנחנו יכולים להיות רגועים כשנפעיל join מחדש על אותה רשימה שחזרה מ split ולדעת שנקבל בדיוק את המחרוזת המקורית:

>>> text = 'split    and    join'
>>> ' '.join(text.split(' ')) == text
True

לעשות את האימייל נפלא שוב

27/11/2020

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

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

חיסרון שני בגישה הוא שאנחנו תקועים עם הממשק וחיבור המקשים שג'ימייל בחרו בשבילנו.

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

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

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

  1. לשמור עותק של כל המיילים אצלכם על המכונה

  2. לקרוא ולכתוב אימייל דרך תוכנת דואר משורת הפקודה שנקראת mutt

  3. לחפש בהודעות דואר ואנשי קשר גם כשאתם לא מחוברים לרשת משורת הפקודה באמצעות mu

המשך קריאה

יש לך טכנאי מזגנים מומלץ?

26/11/2020

  • יש לך הנדימן להמליץ לי?

  • יש לך טכנאי מזגנים טוב להמליץ?

  • יש לך טכנאי מזגנים שמכיר טוב מזגני טורנדו?

  • יש לך טכנאי מזגנים שמכיר טוב מזגני טורנדו ישנים?

  • יש לך טכנאי מזגנים שמכיר טוב מזגני LG תעשייתיים משנת 2008?

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

בתור פרילאנסרים בתוכנה אתם יכולים לבחור את המשבצת שלכם. במקום להיות "מתכנתת Mobile" את יכולה לבחור להיות:

  • זאת שיודעת למצוא ולתקן זליגות זיכרון ביישומי Objective C

  • זאת שיודעת להתאים את הקוד לכל מכשירי Android שיצאו אי פעם

  • זאת שיודעת לכתוב פלאגינים ל React Native כדי לחבר יותר יכולות של המכשיר לאפליקציות RN

  • זאת שיודעת איך לתקן את הקוד כדי שאפל יסכימו להכניס את האפליקציה לחנות

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

התמדה (או: מה עושים עם הקול הזה בראש שצועק לך "תברח!")

25/11/2020

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

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

...

אני נזכר בבחור הזה כל פעם כשאני שומע את הקול הזה בתוך הראש שצועק עליי-

"אתה לא תצליח לכתוב את הקוד הזה"

"ממילא המערכת תהיה מלאה באגים"

"אין סיכוי שזה יעבוד אי פעם"

"לא חבל לבזבז את הזמן על דברים שלא יצא מהם כלום?"

"די"

"הגיע הזמן לעשות הפסקה"

"ארוכה"

"צא"

"לך"

"תברח!"

...

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

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

הפונקציה reduce וסימן חלוקה ב 19

24/11/2020

אחד הפוסטים שעלה היום בהאקרניוז סיפר על סימן חלוקה חמוד ב 19:

  1. מסתכלים על מספר מימין לשמאל (סיפרה אחרי סיפרה)

  2. כופלים את הסיפרה הימנית ביותר ב 2 ומחברים לה את הסיפרה הבאה

  3. את התוצאה כופלים ב 2 ומחברים לה את הסיפרה הבאה

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

בקוד זה נראה כך:

function reduceMod19(n) {
  let accumulator = 0;
  while (n > 0) {
    let digit = n % 10;
    accumulator = accumulator * 2 + digit;
    n = Math.floor(n / 10);
  }

  return accumulator;
}

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

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

digits.reduce((acc, val) => acc * 2 + val, 0);

אני הולך לעבור על כל הרשימה שנקראת digits אחד-אחד, ועבור כל אלמנט אני אכפול את מה שחישבתי עד עכשיו ב-2 ואוסיף את הדבר החדש.

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

function reduceMod19(n) {
  let digits = String(n).split('').map(d => Number(d));
  return digits.reverse().reduce((acc, val) => acc * 2 + val, 0);
}

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

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