In AngularJS, everything has an associated scope. Scopes are organized in a hierarchy. There is a $rootScope object, the parent of all the scopes of the AngularJS application, and there are scopes created by some directives. The scope hierarchy is coherent with the DOM tree hierarchy. Whenever a scope-creating directive is encountered in the DOM tree, a new scope is created.
A controller creates a new scope, so we can define our model variables on that scope. We can also define functions on the $scope object.
The $scope argument in the simpleController function is the scope associated to our new controller. The scope is created for us by AngularJS and made available to our controller function through Dependency Injection (DI). Dependency Injection simply means that we declare that our function depends on a $scope object (specifying it as a function argument) and AngularJS should make it available for us so we can use it inside the function.
In the example, the firstName and lastName variables and the getFullName function are defined in the $scope object managed by our simpleController. We don't need to specify the $scope object in the HTML template because it's implicit in the DOM tree rooted where the ng-controller directive is specified.