Pages

Kotter's Steps to Change: A Case Study 08 November, 2013

Recently I've witnessed a change in management. With these management changes, came ideas on how work could be done differently to produce some fantastic results. After everything was said and done, there was an interesting division in the group. Many people liked the old way, and many people liked the new way. Regardless of whether the change was a good thing, I thought it would be interesting to use this experience as a case study for change.

John Kotter has taught leadership courses at Harvard, and is known for an eight step process for bringing about change. These eight steps need to happen in the outlined outlined order. Here are the steps.

Kotter's 8 steps What I observed
1Create urgencyCuriosity/excitement/fear of management changes/new vision
2Form a group of advocatesNew hires under new management
3Get the vision rightWe can be the best...
4Communicate to get buy inHappened hour by hour
5Empower actionBudgets/Autonomy were given
6Create short term wins???
7Don’t give up???
8Work changes into the cultureThis happened early in the process

So, did it work? Many people are now onboard with some general dreams of improvement, but the division I mentioned still exists between those who were for the change, and those who were against it. In this example, three things diverged from Kotter's process:

  1. It is debatable if there were short term wins
  2. The short term wins that existed were not observed by everyone
  3. Overall culture changes happened to early (before the benefits were seen)

It would seem that for this case, John Kotter was correct. I believe that if the three points that diverged from Kotter's process were done as he outlined, the change would have been embraced by most people, and there would be no division.

Here are the takeaways:

  • Short term wins are necessary
  • They need to be seen by everyone
  • Culture can't change until they come
Make sure these steps don't go awry, and you'll see your changes take place with the lowest amount of pushback.

Mobile apps: Native or Web? 18 October, 2013

We usually write web apps in order to sell a product. Often the web app is the product or service we sell. At some point, the question will probably arise: Should we write native mobile versions of our web app. Here are some obvious pros and cons for native mobile apps:
Pros for native apps
1 - Launching an app is usually easier than navigating a browser
2 - You don't have to login every time
3 - You don't wait for script or content downloads, just network calls

Cons for native apps
1 - Apps are harder to update than websites
2 - Development other than web is required (more $ and people)


Under certain circumstances, these pros and cons might not matter. You may be able to save a bookmark on the home screen. Your browser could remember login info for you. Your scripts could be small. You could have continuous deployment. Depending on your site complexity, performance may be the same. Point #1: Not all your users will know-how/want-to/be-able-to bookmark, login, or buy fast devices. Native mobile apps make sense when you are targeting these time-sensitive/budget-conscious customers. That's the customer-resource based reason.

Now, let's look at the rising-competition based reason. Because of the increasing sophistication of browsers and js libraries, a lot of web apps look really good. What then, differentiates your product from a competitor's product? Besides price and the actual idea or feature set, there is UI and UX.

Design is a differentiator. If you believe that good design matters and want a good design, you will have to ask yourself how custom or dynamic your design should be. It's how real and usable things can look. Pixel level UI control is how that's accomplished. Companies have tried to fix this in the web. There's been ActiveX, VML, Browser DirectX, DOM Manipulation, Flash, and Canvas. These were aimed at getting more UI/UX control, some with good frame rates.



So, let's compare UI/UX control on native apps to that of the web using the most direct control mechanisms that users have access to: Canvas Web Elements vs. Custom Android UI Components. Both have pixel level control, but only one is available to every device running that platform. Canvas doesn't work with some browsers, but Custom Android UI Components work with every Android smartphone. Point #2: If you need the extra differentiation in your UI/UX, get more pixel level control. Native mobile apps make sense when you need to differentiate your UI/UX more.

Eventually, mobile OSes will get ironed out and browsers will improve. Everyone will be on fast mobile devices, and have fast connections. Until then however, many native apps just feel awesome when compared to their web counterparts. The only question right now is whether that awesomeness will draw sufficient users to interact with xyz more than a standalone web experience. Hook up some analytics, and you'll get an idea of how you should proceed.

First Impressions: Dart (DartLang) 02 May, 2013


Dart is a language that can compile down to javascript. It also will make command line apps that run in a VM. It has some nice language features, including with being able to write javascript with compile time static type checks. It also includes DOM manipulation based on selectors. I might use this language for some tools.

Tools

Dart tools are pretty good. The Eclipse plugin had an issue, but the standalone Dart IDE worked great. I had no issues with the stand alone version's logging, warnings, errors, running, or auto-completion.


Speed

It's not fast.


Database Access

Fourth party support is needed for database drivers. By this I mean that DB vendors don't have Dart drivers and there is a small amount of support for third party support for the third party vendor drivers.

Intermingling Static and Dynamic Types

int a;
var b;

Implicit String Evaluation

int a = 5;
String b = "I have $a apples";

Underscores Control Visibility

//private:
int _i;
//public:
int i;

Everything is an Object

5.toString();
1 however is not == true

One Line Functions

//Instead of:
int add(int a, int b) {
  return a+b;
}
//You can do this:
int add(int a, int b) => a+b;

Function Parameters Can be Default / Optional

int add(int a, int b, [int c]) {
  if (?c) print(c); //c was passed
}add(a:6, b:2);

Closures

void main() {
  var f = add;
  f(2,3);
}
int add(int a, int b) {
  print(a+b);
}

Typecasting

Typecasting in Dart is a little different. You use the as keyword:
(someObject as Animal).eat();

Shorthand for Caller reuse

Meet the Cascade Operator.
class test {
  func1() {print("in 1");}
  func2() {print("in 2");}
  func3() {print("in 3");}
}
void main() {
  var t = new test();
  t..func1()
    ..func2()
    ..func3();
}

Easy Object Construction

Observe the absence of a constructor body, yet x gets set.
class test {
  int x;
  test(this.x);
}
void main() {
  var t = new test(6);
  print(t.x);
}

Constructor Delegation

Non-verbose constructor delegation.
SomeClass.myDefaultConstructor(x, y) : this(x, y, 0);

The Factory Keyword

There is a factory keyword to designate constructors that will not create new objects, even though you are using the new keyword when executing the constructor
factory Person(String name) {
  //Get a person from cache and return it
}

Implicit getters/setters

By default, getters and setters exist for all class variables. Extra ones can be created like this:
class Person {
  int baggageWeight;
  int personWeight;
  int get totalWeight => baggageWeight + personWeight;
}
void main() {
  Person p = new Person();
  int total = p.totalWeight;
}

Operator Overloading

A great return from C++.
class Person {
  int age;
  int operator +(Person p) {
    return this.age + p.age;
  }
}
void main() {
  Person p1 = new Person();
  Person p2 = new Person();
  p1.age = 20;
  p2.age = 30;
  int total = p1+p2;
  print(total);
}

Annotations

Dart annotations are easy to declare. They're just classes that usually start with lower case characters.
class asdf {}
@asdf
class Person{}

Name Spacing

You can use the as keyword to alias some package you've imported
import package:a/lib;
import package:b/lib as img;

The library and packaging system

So this is a little different than Java/C++ packages/headers
Libraries: The code part of a package that uses library and part keywords to modularize code for a package.
Packages: A package is a config + Library. The config lets you to define dependencies of a package using a Pubspec file (yaml).

Threads (Futures & Isolates)

Futures allow you to run callback after a Timer or thread(Isolate) has completed or erred out.
Isolates(Threads that are isolated from each other) are just functions passed to spawnFunction(). They can talk to other threads using send(), receive(), and call().
import 'dart:isolate';
import 'dart:async';
go1() {
  port.receive((msg, reply) {
    print ('i got $msg');
  });
}
Future go2(){
   Completer completer = new Completer();
   new Timer(new Duration(seconds:1), () {completer.complete("Time is up");});
   return completer.future;
}
void main() {
  var sendPort = spawnFunction(go1);
  sendPort.send("hello"); //Might not get processed if main exits too fast
  sendPort.call("a better way to send").then((reply) {print("sent");});
  go2().then((String result) {print(result);});
}

First Impressions: Go (GoLang) 30 April, 2013


Go is a language that mixes old and new concepts. They use automatic memory management, but also bring back pointers and unsigned primitives. Other differences include forcing defensive style. It is a statically typed language, which helps find errors at compile time rather than waiting for a runtime error/test to catch the problem. Something else that I really like is the basic web site readiness. Go comes built with web technologies built in.

I think it's a decent language, but for me to spend more time using GO, it needs:
1 - a unique name (try to google 'go' + something)
2 - to be built out more (ex: compiler optimizations, improved web site readiness)
3 - better data integration (it feels like the only good support is for AppEngine's Datastore)

The use of GO seems to be restricted to a few startups, or to tools of better known or longer lived companies. Here's a list of some features I wanted to highlight:


Tools

The tools are still ramping up. Getting automatic building and completion on OSX seems like it was more of a pain than it should have been. The windows setup was pretty simple. It gives you an idea of what is available, but isn't quite as smooth as your standard Eclipse or VS auto-complete.


Speed

Another thing that needs some love is the compiler optimizations. I ran a couple of benchmarks. I know these are specific cases, but  for a compiled binary, it should have out preformed Java. Instead Java was at least twice as fast. The two tests I ran were SHA2 generation, and Fibonacci generation.

Built In Web Framework

There is no need for an additional or external web container. No Tomcat. No Rails. It runs it's own server and it's built in.
package main
import (
  "net/http"
)
func main() {
  http.HandleFunc("/", someHandlerFunction)
  http.ListenAndServe(":8080", nil)
}

HTML Templating

Built into the language is the ability to markup HTML with GO data:
.go file:
x, y := template.ParseFiles("some.html")
x.Execute(httpResponse, dataModel)
.html file:
<a href="someLink">{{.LinkTitle}}</a>

Multiple Return Values

func getPair() (int,int) {
  return 1,2
}

Signed & Unsigned Types

a int8 = 127b uint8 = 255

Forced Style

{}s required for one line if/for blocks. Not doing this creates a compile time error. Also, else statements must be on the same line as it's braces.
Right:
if i==0 {
  //Something
} else {
  //Something else

Wrong (no braces):
if i==0
  i = -1

Wrong (closing if/starting else braces are on different lines):
if i==0 {
}
else {
}

Unused Code

Unused code (variables/imports/etc.) will create compile time errors instead of warnings.

Initializing Statements for if Blocks

if i:=math.Max(a,b); i==5 {
  //Do something, possibly using i
} else {
  //Use i here too 
}  

Easy Small Object Construction & Assignment

Java:
class Pair {
  int a;
  int b;
  public Pair(int a, int b) {
    this.a = a;
    this.b = b;
  }
}
new Pair(1, 2);
V.S.
GO:
type Pair struct {  a int  b int}Pair{1,2}


Pointers (No Pointer Arithmetic)

func mod(i *int) {
    *i++
}
func main() {
    i:=4
    mod(&i)
    fmt.Println(i)
}

Variable Struct Construction Args

type fourPropertyStruct struct {
    a,b,c,d int
}
func main() {
    fmt.Println(fourPropertyStruct{b:4,d:7})
}


Simpler Syntax for Arrays

someArray[firstElement:lastElement-1] will return the appropriate subset of someArray[]. Missing indexes imply beginning or end ([:3] or [3:] for example)


One Form of For

Instead of a multi step for and a simple iterator based for, one form is used:
var list = []int{1, 2, 4, 8, 16}
func main() {
    for i, v := range list {
        fmt.Printf("index: %d, value: %d\n", i, v)
    }
}
To keep a single For form, _ is used when you don't need either the index or value
for _, value := range pow {
    fmt.Printf("%d\n", value)
}

Object Creation

new creates New Objects
make creates New Arrays & Maps
a:=new(SomeStruct)
b:=make([]int, 5)
Maps are declared: map[keyType]valType
maps can return a key, boolean pair describing what the value is/if the key existed

Simultaneous Assignment

x,y = y,x+y
Temp variables are no longer needed!


No Break Statement Needed in Switch Statements

switch ret {
  case 1: //Do something
  case 2: //Do something else
  default:
}

No Classes. Just Structs with Methods Appended

interface types can have method signatures defined in them. a type implements an interface when it has those methods, not by tagging it as that interface
type Greeter interface {
    Greet() string
}

Errors Implemented by Having an Error()(string) Method

You don't tag a struct or object with an interface. If an object has the methods defined in an interface, it is automatically-polymorphically-compatible.

Easy Threading

go someMethod, will launch that method on a separate thread. When you combine this with channels (a report back mechanism), concurrency becomes simple compared to many other languages:
func getInfoFromThread(x chan string) {
    x <- "hi"

}
func main() {
    x := make(chan string)
    go getInfoFromThread(x)
    z := <-x br="">    fmt.Println(z)
}

Transistors and Computer Science 22 March, 2013

It feels like there are a multitude of developers who talk about Arduino, Raspberry pi, and computer hardware in general. This being said, I haven't observed many that add this type of knowledge to their arsenal. Over the last year, I caught myself doing the same thing, so I finally took the plunge.

Understanding topics like Ohm's law and current are necessary to get into any detail. If you're a hobbyist, Maker Shed has a great intro. But for a developer looking for the executive summary, the transistor is a good place to start. Not only is the transistor something your dev box is based on, but it has the fascinating application of being able to represent boolean logic in hardware. This lays the foundation for all those truth tables you did in your Computer Architecture/Systems classes.

Here's an example.
Inputs: A, B
Output: C

Here's a truth table for C = f(A, B):
ABC
000
010
100
111

A boolean expression that calculates A and B based on this truth table would be:
A AND B, also commonly written as A∧B or A && B.
If both A and B are 0, or either A or B are 0, C equals 0.
C is only 1 if both A and B are 1.

Here's where transistors come into play. Basic Bipolar Junction Transistors take two inputs, and have a single output. They are perfect for creating AND, OR, NOT, XOR, NAND, and NOR operations. Transistors may need to be chained together while acting as a series of cascading switches to get such benefits, but they can do it.

Once we chain enough of these logic gates together, we can do more complicated computations.


Here's a transistor schematic symbol:
Here's a schematic for an AND gate using two transistors:

Simple, yet interesting.