Slide 1

Slide 1 text

JavaScript Workshops Advanced JavaScript

Slide 2

Slide 2 text

“ For at least the next decade, you won't be able to move forward witout a good understanding of #javascript. — Orion Henry (Heroku)

Slide 3

Slide 3 text

#1: Variables Let's create a variable called m e v a r m e = " D i m i t r i " ; What happens when you enter: What about: c o n s o l e . l o g ( m e ) ; c o n s o l e . l o g ( y o u ) ;

Slide 4

Slide 4 text

#1: Variables Will it be t r u e ? " 1 " = = 1 ; " " = = n u l l ; 0 = = n u l l ; [ ] = = " " ;

Slide 5

Slide 5 text

#1: Variables JavaScript is dynamically typed and "autocasts" types to compare. This can lead to funny behavior, for example: BUT: 0 = = " 0 " ; / / t r u e 0 = = " " ; / / t r u e " 0 " = = " " ; / / f a l s e Always use = = = " 1 " = = = 1 ; / / f a l s e [ ] = = = " " ; / / f a l s e 0 = = = " 0 " ; / / f a l s e 0 = = = " " ; / / f a l s e

Slide 6

Slide 6 text

Tip 1: Always Use = = =

Slide 7

Slide 7 text

#2: Scopes JavaScript uses scopes: f u n c t i o n f o o ( ) { v a r f o o = " b a r " ; f u n c t i o n b a r ( ) { c o n s o l e . l o g ( f o o ) ; / / " b a r " o r e r r o r ? } } What about: f u n c t i o n f o o ( ) { v a r f o o = " b a r " ; f u n c t i o n b a r ( ) { v a r f o o = " b a z " ; c o n s o l e . l o g ( f o o ) ; / / " b a r " o r " b a z " ? } c o n s o l e . l o g ( f o o ) ; / / " b a r " o r " b a z " ? }

Slide 8

Slide 8 text

#2: Scopes v a r e = " f o o " ; c o n s o l e . l o g ( e ) ; / / ? t r y { t h r o w " b a r " ; } c a t c h ( e ) { c o n s o l e . l o g ( e ) ; / / ? } c o n s o l e . l o g ( e ) ; / / ? Scopes are everywhere v a r a = " f o o " ; c o n s o l e . l o g ( a ) ; f u n c t i o n b a r ( ) { i f ( t r u e ) { v a r a = " b a r " ; c o n s o l e . l o g ( a ) ; } c o n s o l e . l o g ( a ) ; / / " f o o " , " b a r " o r e r r o r ? } Well... ALMOST everywhere

Slide 9

Slide 9 text

Tip 2: There Is No Such Thing As A Block Scope!

Slide 10

Slide 10 text

#2 Scopes Each scope has access to its outer scope. There is also a "root" scope, which we call the global scope In browsers this is w i n d o w On Node.js it is g l o b a l Be careful, if you don't use v a r in front of your variable, it will create the variable on the global scope! f u n c t i o n f o o ( ) { a = " b a r " ; } f o o ( ) ; c o n s o l e . l o g ( w i n d o w ) ;

Slide 11

Slide 11 text

Tip 3: Always Use v a r To Create Variables!

Slide 12

Slide 12 text

#3: Objects To create a new object, you can use: v a r m e = { f i r s t n a m e : " D i m i t r i " , n a m e : " M e s t d a g h " } ; But what about classes & constructors?

Slide 13

Slide 13 text

#3: Objects JavaScript uses prototypes: v a r O p t i c i e n = f u n c t i o n ( f i r s t n a m e , l a s t n a m e ) { t h i s . f i r s t n a m e = f i r s t n a m e ; t h i s . l a s t n a m e = l a s t n a m e ; t h i s . s a y N a m e = f u n c t i o n ( ) { c o n s o l e . l o g ( t h i s . f i r s t n a m e + " " + t h i s . l a s t n a m e ) ; } ; } ; v a r m e = n e w O p t i c i e n ( " D i m i t r i " , " M e s t d a g h " ) ; m e . s a y N a m e ( ) ; O p t i c i e n appears to be a normal function, but it can be instantiated using the n e w keyword. We call this a prototype.

Slide 14

Slide 14 text

#3: Objects The difference between classes vs prototypes in JavaScript is that they can be changed at runtime: v a r P e r s o n = f u n c t i o n ( f i r s t n a m e , l a s t n a m e , j o b ) { t h i s . f i r s t n a m e = f i r s t n a m e ; t h i s . l a s t n a m e = l a s t n a m e ; t h i s . j o b = j o b ; } ; P e r s o n . p r o t o t y p e . s a y J o b = f u n c t i o n ( ) { c o n s o l e . l o g ( t h i s . j o b ) ; } ; P e r s o n . p r o t o t y p e . s a y N a m e = f u n c t i o n ( ) { c o n s o l e . l o g ( t h i s . f i r s t n a m e + " " + t h i s . l a s t n a m e ) ; } ; v a r m e = n e w P e r s o n ( " D i m i t r i " , " M e s t d a g h " , " I T C o n s u l t a n t " ) ; m e . s a y J o b ( ) ; m e . s a y N a m e ( ) ;

Slide 15

Slide 15 text

#3: Objects Inheritance is also possible through prototypal inheritance: v a r O p t i c i e n = f u n c t i o n ( f i r s t n a m e , l a s t n a m e ) { P e r s o n . c a l l ( t h i s , f i r s t n a m e , l a s t n a m e ) ; / / s u p e r ( f i r s t n a m e , l a s t n a m e ) t h i s . j o b = " I T C o n s u l t a n t " ; } ; O p t i c i e n . p r o t o t y p e = n e w P e r s o n ( ) ; / / O p t i c i e n e x t e n d s f r o m P e r s o n v a r m e = n e w O p t i c i e n ( " D i m i t r i " , " M e s t d a g h " ) ; m e . s a y J o b ( ) ; m e . s a y N a m e ( ) ;

Slide 16

Slide 16 text

#3: Objects Overriding a function is also possible: O p t i c i e n . p r o t o t y p e . s a y J o b = f u n c t i o n ( ) { c o n s o l e . l o g ( " A w e s o m e " + t h i s . j o b ) ; } ;

Slide 17

Slide 17 text

Tip 4: Prototypes Can Be Inherited, Extended And Overriden Any Time.

Slide 18

Slide 18 text

#4: Functions Functions are multifunctional: We can use them as simple functions We can use them as prototypes F u n c t i o n i n s t a n c e o f O b j e c t ; / / t r u e O b j e c t i n s t a n c e o f F u n c t i o n ; / / t r u e

Slide 19

Slide 19 text

#4: Functions You can do a lot with functions, you can even call them directly: ( f u n c t i o n ( ) { c o n s o l e . l o g ( " I ' m e x e c u t e d d i r e c t l y " ) ; } ( ) ) ; This is an Immediately Invoked Function Expression or an IIFE.

Slide 20

Slide 20 text

#4: Functions Common use case for IIFE's: ( f u n c t i o n ( $ ) { } ( j Q u e r y ) ) ; Many libraries use the dollar sign ($ ) IIFE's have their own local scope

Slide 21

Slide 21 text

#4: Functions Remember that we should always check with = = = , what about: v a r h a s N a m e = f u n c t i o n ( p e r s o n ) { r e t u r n p e r s o n . n a m e ! = = u n d e f i n e d ; } ; c o n s o l e . l o g ( h a s N a m e ( { n a m e : " D i m i t r i M e s t d a g h " } ) ) ; ... works fine, don't you think so?

Slide 22

Slide 22 text

#4: Functions However, in ECMAScript 4 and lower (everything up to IE8), u n d e f i n e d is a mutable object: w i n d o w . u n d e f i n e d = " D i m i t r i M e s t d a g h " ; v a r h a s N a m e = f u n c t i o n ( p e r s o n ) { r e t u r n p e r s o n . n a m e ! = = u n d e f i n e d ; } ; c o n s o l e . l o g ( h a s N a m e ( { n a m e : " D i m i t r i M e s t d a g h " / / T h i s w i l l r e t u r n f a l s e i n I E 8 ! ! ! } ) ) ;

Slide 23

Slide 23 text

No content

Slide 24

Slide 24 text

#4: Functions To solve this, you can use IIFE's as well: ( f u n c t i o n ( $ , u n d e f i n e d ) { } ( j Q u e r y ) ) ; Add u n d e f i n e d as the last argument Nothing is passed to it, so it's REALLY u n d e f i n e d

Slide 25

Slide 25 text

#4: Functions Functions into detail: v a r i n c r e m e n t = f u n c t i o n ( n u m ) { n u m + = 1 ; } ; v a r n u m = 2 ; i n c r e m e n t ( n u m ) ; c o n s o l e . l o g ( n u m ) ; / / ? Just like Java, arguments are passed by value

Slide 26

Slide 26 text

#4: Functions Functions into detail: v a r c h a n g e N a m e = f u n c t i o n ( p e r s o n ) { p e r s o n = { n a m e : " J o h n D o e " } ; } ; v a r m e = { n a m e : " D i m i t r i M e s t d a g h " } ; c h a n g e N a m e ( m e ) ; c o n s o l e . l o g ( m e . n a m e ) ; / / ? Also, objects are passed by reference.

Slide 27

Slide 27 text

#4: Functions Let's try to write the numbers 1 to 10 with one second delay each. Will this work? No!, think of . f o r ( v a r i d x = 1 ; i d x < = 1 0 ; i d x + + ) { s e t T i m e o u t ( f u n c t i o n ( ) { c o n s o l e . l o g ( i d x ) ; } , 1 0 0 0 * i d x ) ; } Tip 2

Slide 28

Slide 28 text

No content

Slide 29

Slide 29 text

#4: Functions Hmmzz... IIFE's solve everything right? Let's try them! f o r ( v a r i d x = 1 ; i d x < = 1 0 ; i d x + + ) { ( f u n c t i o n ( n u m ) { s e t T i m e o u t ( f u n c t i o n ( ) { c o n s o l e . l o g ( n u m ) ; } , 1 0 0 0 * n u m ) ; } ( i d x ) ) ; } It works because arguments to a function are ... passed by value

Slide 30

Slide 30 text

No content

Slide 31

Slide 31 text

Tip 5: Always Wrap Your Code In An IIFE

Slide 32

Slide 32 text

Now Class, What Did We Learn Today? Always use = = = There is no such thing as a block scope! Always use v a r to create variables! Prototypes can be inherited, extended and overriden at any time. Always wrap your code in an IIFE

Slide 33

Slide 33 text

No content

Slide 34

Slide 34 text

The End Go Home And Code Some JavaScript!