Wednesday, November 19, 2014

JavaScript notes - Part 2

This post is in continuation of this one http://tunephp.blogspot.com/2014/11/javascript-notes-part-1.html. It will contain notes about JavaScript Inheritance, Arrays, Regular Expressions, Style, Beautiful Features, Awful parts and Bad Parts.

Inheritance

  1. JavaScript being a loosely typed never casts. What matters about object is what it can do, not what it is descended from.
  2. Every function gets a prototype object because the language does not provide a way of determining which functions are intended to be used as constructors. The constructor property is not useful, it is the prototype object that is important.
  3. If all of the state of an object is private then the object is tamper-proof. Properties in the object can be replaced or deleted, but the integrity of the object is not compromised.
  4. If we create object in functional style and all of the methods of the object make no use of "this" or "that" then the object is durable. A durable object is simply a collection of functions that act as capabilities. A durable object cannot be compromised.

Arrays

  1. JavaScript has an object that has some array like characteristics. It converts array subscripts into string that are used to make properties. It is significantly slower than a real array.
  2. Arrays have useful set of built in methods than objects.
  3. Arrays in JS can contain any mixture of values. example: var myArray = ['', 0, undefined, "hello", null, {'key': 'value'}, [0, 1, 2, 3]];
  4. Every array has a length property and length is not an upped bound. If you store an element with a subscript that is greater than or equal to the current length the length will increase to contain the new element. There is no array bounds error.
  5. The length is the largest property name in the array plus one, but not necessarily the number of properties in the array. example: var myArray = []; myArray[1000000] = true; myArray.length = 1000001; // myArray contains one property
  6. The length can be set explicitly. Making then length larger does not allocate more space for the array. Making the length smaller will cause all properties with a subscript that is greater than or equal to the new length to be deleted.   A better way to add new element is to use push() function.
  7. Arrays are objects so the delete word can be used to delete element in an array. That leaves a hole but you can use splice() method to cleanly remove it from an array or to replace it with new one.
  8. Since arrays are objects "for in" statement can be used to iterate over the elements. The order is not necessarily incremental, so properties from the prototype chain can be dredged up. Use "for" statement instead if the order is important.
  9. Common rule when property names are small sequential integers is to use array, otherwise use object. 
  10. JavaScript cannot differentiate between arrays and objects since arrays are objects. Also we can add custom functions to Array.prototype
  11. It is not useful to use Object.create() on arrays since it creates object but not array. It will not have the length property or other functions that have arrays. 
  12. You can use Array.prototype.slice() method to create shallow copy of a portion of an array into a new array object. example: var myNewArray = myOldArray; myNewArray is not new object containing the same values from myOldArray, it is just a reference to the same myOldArray in memory. That means, changes to myNewArray affect myOldArray. To create new array object with the same values of myOldArray use this command: var myNewArray = myOldArray.slice(0);

Regular Expressions

  1. Many JS features were borrowed from other languages. The syntax is from  Java, functions from Scheme, prototypal inheritance from Self. JS regular expressions were borrowed form Perl.
  2. Regular expressions have significant performance advantage over equivalent string operations in JavaScript.

Style

  1. If a program is able to clearly communicate its structure and its characteristics it is less likely to break when it is modified in the never too distant future. 
  2. JS code is often sent directly the the public. It should always be of publication quality.
  3. Put spaces around all infix operators except for dot (.) and square bracket ([) because they have higher precedence.
  4. Put space after every comma and colon. 
  5. Put at most one statement per line. If statement doesn't fit in one line break it after comma or binary operator.
  6. Always use blocks {} with structured statements like while and if because it is less error prone.
  7. With JS you should always use Kernighan and Ritchie style, putting the { at the end of a line instead of the front because it avoids a horrible design blunder in JS's return statement.
  8. Declare all variables at the top of each function. JS doesn't have a block scope but it has a function scope. 
  9. Never allow switch cases to fall trough to the next case.
  10. Use single global variable to contain one application or library. Every object has its own name-space. Use of closure provides information hiding increasing the strength of your modules.

 Beautiful Features

  1. JS good stuff includes: functions as first class objects, dynamic objects with prototypal inheritance, object literals and array literals.
  2. Features have a specification cost, a design cost and a development cost. There is a testing cost and a reliability cost. The more features there are the more likely one will develop problems or will interact badly with another.
  3. In software systems there is a storage cost which become negligible but in mobile is becoming significant again. (Ascending performance cost because Moor's Law doesn't apply to batteries). Features have documentation cost which increases training cost.

Awful Parts

  1. A global variable is a variable that is visible in every scope. Because global variables can be changed by any part of the program at any time they can complicate the behaviour of the program. Use of global variables degrades the reliability of the programs that use them.
  2. JS requires global variables. JS doesn't have a linker. All compilation units are loaded into a common global object.
  3. Always use var keyword before declaring a variable. It links the new variable with the global "this" if var is not present.
  4. Always out { after return since JS will try to add semi colon after return which can produce bugs. There is no warning, return will return undefined value.
  5. If you have a need to name properties or objects using reserved words use quotes or brackets {} like this object = {case: value}
  6. JS characters are 16-bit  wide. Today Unicode contains characters that can be 32-bit wide. JS considers them as two distinct characters.
  7. typeof null returns 'object'. A better check is my_value === null. null is falsy, all objects are truthy.
  8. typeof /a/ returns 'object' or maybe 'function', it should return 'regexp' but it doesn't.
  9. Always provide parseInt() with radix parameter. example: parseInt("08", 10); It stops when it sees nondigit so parseInt("16") and parseInt("16 tons") produce the same result 16.
  10. The plus (+) operator can concatenate and can add numbers. If you plan to add numbers make sure both operands are numbers.
  11. 0.1 + 0.2 is not equal to 0.3. This is a consequence to having adopted the IEEE Standard for binary  floating point arithmetic (IEEE 754). Fortunately integer arithmetic in floating point is exact, so decimal errors can be avoided by scaling.
  12. NaN is a special quantity defined by IEEE 754. It stands for Not a Number. If NaN is operand in arithmetic operation than NaN will be the result. NaN === NaN returns false while NaN !== NaN returns true.
  13. JS does not have real arrays. There is no need to give them a dimension and they never generate out of bound errors. But their performance can be considerably worse than real arrays. The typeof operator thinks that arrays are objects.
  14. The arguments array is not an array. It is an object with length property and it lacks the array specific methods.
  15. undefined and NaN are not constants. They are global variables and you can change their values. That should not be possible, yet it is. Don't do it. :D
  16. hasOwnProperty() of Object.prototype is a function and it can be replaced with different function or with value that is not a function. Don't do it :D

Bad Parts

  1. Don't use == and !=, use === and !== instead. == and != do a type coercion while === and !== do check the type of operands but don't do type coercion.
  2. "with" statement was intended to provide shorthand when accessing properties of an object. Its results can be unpredictable so avoid it.
  3. eval is evil, don't use it.
  4. Don't use continue
  5. Never leave a fall trough in switch statement.
  6. Avoid using ++ and --, use += and -= instead.
  7. JS is rarely used for bit manipulation. Bitwise operators are far from the hardware and their result is processed slower than in other languages.
  8. Avoid using "new Object" and "new Array", use {} and [] instead. Don't use "new Boolean", "new Number" and "new String"
  9. Avoid using "new" keyword. If you forget to create new object with "new" keyword, the new object will be bound to the global name-space, which is bad.
  10. Avoid using void keyword.

Friday, November 14, 2014

"JavaScript: The Good Parts" - book review

In this post I'll explain my thoughts on "JavaScript: The Good Parts" written by Douglas Crockford. It is fairly old book written in 2008 but still does the good job of teaching you what to use and what not to use from JavaScript. As the author says, this book has lot of information packed in about 150 pages, which means you have to read at least twice each chapter. Yes I passed each chapter twice and also spent some time writing the code from the book in Firefox/Firebug just to see how it goes. I think more examples to practice would be much better for the book as it lacks them. But in the end you would certainly need to read another book to learn how to code proper JavaScript modules, patterns, etc... I am planning to read another book because this one is not enough to get you going with JS. My recomendation for next book would be this one: "JavaScript Patterns" - by Stoyan Stefanov, it has about 240 pages which is enough.

The book is structured in 10 chapters and with 5 appendices, A-E. My suggestion is to read all chapters includding the appendices. Appendix D is just the railway diagrams, so you may skip it.
Chapters:
  1. Good Parts. This chapter contains basic info about JS and how to set up testing ground for other code examples in the book. Don't skip it. 
  2. Grammar. Contains basic information about reserved keywords in JS, data types, expressions, functions etc...
  3. Objects. Explain how to work with Objects in JavaScript, how to create new object, how to retrieve infrormation from object, object prototype, reflection, enumeration, delete operator, etc...
  4. Functions. Dives into JavaScript function basics. How to create new function, how to invoke a function, this and arguments objects of a function, its connection with objects. Each function is an object so you can add a function to its prototype. Function scope, closure, function modules, cascade (builder pattern), curry and memoization.
  5. Ineritance. Inheritance types, implementing standard OOP in JS (pseudoclassical) inheritance, prototypal and functional inheritance. Very important chapter, don't skip it.
  6. Arrays. Array basics, length property, useful array methods, delete operator, enumeration, etc...
  7. Regular Expressions. Dives into JS regular expressions, what are they and how to use them. Couple of basic rules how do RE work. Very useful thing, especially when processing strings. 
  8. Methods. This chapter explains implemented methods that come with JavaScript itself. You may want to skip this chapter but it would be helpful if you read it. 
  9. Style. This chapter explains some techniques how to write error prone JavaScrtipt code. My suggestion is to not skip this chapter. 
  10. Beautiful features. Read this chapter to learn what are the best parts of JavaScript that you should use. Functions as a first class object, Dynamic objects with prototypal inheritance and Object litrals and array literals.
  11. Appendix A. Awful Parts. Explains all of the worse parts in JS and how to avoid them.Global variables, scope, semicolon insertion, reserved words, unicode, typeof operator, parseInt function, + operator, floating point, NaN, phony arrays, falsy values, hasOwnProperty function and Object.
  12. Appendix B. Bad parts. Things you can live with but still should avoid. == vs === operators, with statement, eval function, continue statement, switch fall trough, block-less statements, ++ and -- operators vs += and -= operators, bitwise operators, function statement vs function expression, typed wrappers, new operator, void keyword.
  13. Appendix C. JSLint. An online tool build by Douglas himself. Use it whenever possible to debug your JS code. You may find this tool also useful, http://jsbeautifier.org/
  14. Appendix D. Syntax Diagrams. If you are beginner at programming, these railway diagrams will help you get going. 
  15. Appendix E. JSON. Explains what is JSON, JSON syntax, how to use it securely and a complete script of JSON parser in JavaScript.
 I think this book is not recommended for beginner programmers, but it is good if you are learning JavaScript. Still it lacks more code examples and practices, so you have to read another JS book. My opinion of this book is 4.5/5. It does the job for what is meant to do, aka teaching you pros and cons of JavaScript and how to use or avoid them. You must read this book if plan to code JS programs in future.

Tuesday, November 4, 2014

JavaScript notes - part 1

Hello. In this post I will share some notes I made while reading this book JavaScript: The Good Parts by Douglas Crockford. So it is nothing new or special, this post will serve simply to cover the most important properties of JavaScript. The notes are taken, copied or modified from the book itself. I didn't write them, Douglas did. :)

For part two visit this link: http://tunephp.blogspot.com/2014/11/javascript-notes-part-2.html
 

Good Parts

  1. I can be a better programmer by using only the good parts of a language and avoiding the bad parts.
  2. The API of the browser, Document Object Model (DOM) is quite awful and JavaScript is unfailry blamed.
  3. JavaScript is a language with enromous expressive  power. It is even better when you know what you are doing.
  4. Very good ideas on which JS is build upon are: functions, loose typing, dynamic objects, and an expressive object literal notation. Bad ideas include global variables.
  5. JavaScript has more in common with Lisp and Scheme than with Java. It is List in C - clothing.
  6. JS compilers are unable to detect type errors because JS is loosely typed.
  7. Objects can be created by listing their components (inspired by object literal notation mainly for the creation of the JSON format).
  8. JS has class free object system in which objects inherit properties directly from other objects (prototypal inheritance).
  9. Implementing classical design  patterns in JS can be frustrating but using prototypal inheritance can be rewarding.
  10. JS depends on global variables for linkage. All top level vars are tossed together in a common namespace called global object.

Grammar

  1. JS supports two types of comments, block comments made by /* .. */ charaters and line - ending comment made by two forward slashes // . Comments should be updated and should always describe accurately what the code does. Obsolete comments are worse than no comments.
  2.  Block comments should be avoided as it is unsafe to comment out a block of code. Use line ending comments instead.
  3. The list of reserved words should include theese: undefined, NaN and Infinity but unfortunately it doesn't have them. It is not permited to use reserved word as a name of a variable. Be careful with the three mentioned above.
  4. JS has a single number type. Internally it is represented as a 64 bit floating point number, same as Java's double number type.  There is no separate number type, 1 and 1.0 are the same thing.
  5. 1e2 = 100 = 1 * 10 ^ 2
  6. NaN is a number value produced as result of operation that cannot produce normal result. NaN is not equal to any value including itself. You can detect a NaN value with isNaN(value) function, or you can use isFinite(value) function which returns false if the value is +Infinity, -Infinity, or NaN (Not-a-Number), otherwise it returns true.
  7. Infinity represents all values greater than 1.7976931348623157E+10308
  8. Numbers have methods. JS has Math object that contain set of methods to work on numbers.
  9. A string literal can be wrapped  in single or in double quote. (\) backslash is the escape character. 
  10. All characters in JS are of 16 bit character set (JS was built when Unicode was 16 bit). There is not character type. Today Unicode has more than 65536 different characters represented by 32 bits. Be aware that JavaScript decodes them as two characters instead of single one.
  11. The \u convention allows specifying characters numerically. "A" === "\u0041";
  12. Strings have length property. A string is immutable constant. Once set a new value you cannot change it. However new strings can be made by concatenating two separate strings with + sign.
  13. Unlike many other languages blocks of code surrounded by curly braces {} do not create a new scope, so new variables should be defined at the top of the function, not in blocks.
  14. Falsy values in JS are: false, null, undefined, the empty string '', the number 0, the number NaN. All other values including true, the string 'false' and all objects are truthy.
  15. Use object.hasOwnProperty(variable) function to determine whether the property name is truly a member of the object or was found instead on the prototype chain.
  16. The = operator is used for assignment. Do not confuse it with equality operator ===.

Objects

  1. The simple types of JS include numbers, strings, booleans, null and undefined. All other values are objects.
  2. Numbers, strings and booleans are object like and they have methods but they are immutable.
  3. Objects in JS are mutable nested collections of properties. In JavaScript arrays are objects, functions are objects, regular expressions are objects and of course objects are objects.
  4. Objects in JS are class free. Objects can contain objects.
  5. JS includes prototype linkage, which allows object to inherit properties from another objects. When properly used prototype linkage can reduce object initialization time and memory consumption.
  6. The quotes around a property's name in an object literal are optional if the name would be legal and not a reserved word. Quotes around "first-name" are required but optional around first-name.
  7. If a string expression is a constant and a legal JS name and not a reserved word than the dot ( . ) notation can be used instead.
  8. Attempting to retrieve undefined values from object will throw a TypeError exception.
  9. If there is already a property with given name in an object, new value will just replace the old value. If the propery does't exist the object is augmented with new property. 
  10. Objects are passed around by reference, they are never copied.
  11. Every object is linked to a prototype object from which it can inherit properties. All objects created from object literal are linked to Object.prototype.
  12. The hasOwnProperty() method does not look at the prototype chain of an object.
  13. The "for in" statement can loop over all of the property names in an object. It will include functions and prototype properties as well. The order of the properties/functions listed using "for in" is not necessarily incremental. If the order is important use "for" statement instead. "for" does not cover the prototype properties.
  14. delete operator can be used to remove a property from an object. It will not touch any of the objects in the prototype linkage. So removing a property from object may uncover a property from the prototype object with the same name.
  15. Avoid using global variables. Better create your own application namespace by creating your own global variable in which all your application structure will reside so that it will not interfere with objects/properties from other applications in the global namespace. 

Functions

  1. Functions are the best part in JavaScript. They are commonly used for code reuse, information hiding and composition. Functions in JS are objects linked with Function.prototype which is linked to Object.prototype
  2. Functions can be stored in variables, objects, arrays. Functions can be passed as arguments to function and functions can be returned from functions. Also since functions are objects they can have methods too. Unlike other objects in JS, functions can be invoked.
  3. Function literal has 4 parts. The first is the word "function". The second optional is the name of a function (used by debbugers to identify a function). Function without a name is called anonymous function. The third part is a set of parameters wrapped in braces (). The fourth part is a set of statements wrapped in curly braces {} (The body of a function).
  4. In addtion to the list of parameters in braces (), each function gets two additional params: this and arguments
  5. There are four patterns of invoaction in JS: method invocation, function invocation, constructor invocation and apply invocation (the patterns differ in how the bonus parameter "this" is initialized).
  6. There is no runtime error when the number of arguments and the number of parameters do not match. If there are too many argument values, the extra args are ignored. If there are too few arguments, the missing ones will be substituted with undefined. There is no type checking on the argument values, any type of value can be passed to any parameter.
  7. When a function is invoked with function invocation pattern, it is bound to the global object. If the language would have been designed correctly, the function would be bound to "this" of the outer function. A consequence of this error is that a method cannot employ an inner function to help it do its work because the inner function does not share the method's access to the object as its "this" is bound to the wrong value.
  8. If a function is invoked with the new prefix, then a new object will be created with a hidden link to the value of the function's prototype member and "this" will be bound to that new object.
  9. Functions that are intended to be used with the new prefix are called contrustors. By convention they are kept in variables with a capitalized name. If a contructor is called without the new prefix very bad things can happen without a compile time or runtime warning, so the capitalization convention is really important. The best way to cope with this is to not use new prefix at all.
  10. arugments array gives the function all the arguments that were supplied with the invocation, including excess arguments that were not assigned to parameters.
  11. Because of design error, arguments is not really an array. It is an array-like object. It has the length property but it lacks array methods.
  12. A function always returns a value. If the return value is not specified then undefined is returned.
  13. If the function was invoked with the new prefix and the return value is not an object then "this" (the new object) is returned instead.
  14. A try statement has a single catch block that will catch all exceptions. If your handling depends on the type of the exception, then the exception handler will have to inspect the name to determine the type of the exception.
  15. Unfotunatelly JS does not currently provide tail recursion optimization.
  16. JavaScript doesn't have a block scope but it has function scope. That means all variables should be declared as soon as possible or at the top of the function body.
  17. The good thing about scope is that inner functions get access to the parameters and variables of the functions they are defined within (exception are "this" and arguments object). This is called Closure.
  18. A module is a function or object that represents an interface but that hides its state and implementation.
  19. By using functions to produce modules, we can completely eliminate our use of global variables thereby mitigating one of the worst JS features.
  20. Use of module pattern can eliminate the use of global variables.
  21. JavaScript does not have a Curry method.
  22. Function can use objects to remember the results of previous operations making it possible to avoid unnecessary work. This optimization is called memoization.
  23. By devising functions that produce other functions, we can significantly reduce the amout of work we have to do.