Why lisp ?



A lot of people is scared about lisp syntax.

They hear Lisp is a very powerful language, but the syntax and the lisper indentation makes them cry and run.

This is sad, because Lisp is really a fun language.

When I think about funny languages, I think in python, because it's easy and the funny part is really that you get work done and see the results so soon.

Also, you don't need to care about a lot of things to start working in your stuff.

Even knowing that Python is a funny language, I state that Lisp is even funnier.

You might think the same all newcomers think: "It's really funny to have a lot of fucking parenthesis around? I don't see the funny part"

I understand you, because when one guy sees Lisp code it just sees parenthesis.

Also those parenthesis are indented in a cryptic way, and this is really what makes people run.

We are used to see indentation as a cleaner way to show our code.

If you don't indent your code, people will want to kill you.

The sad part, is the indentation of Lisp conventions is not really a cleaner way to show the code like we are used to see.

For example:

(let ((oh 3)) (+ oh 2))

Those parenthesis are a bit annoying because we don't know why are they, for example, why the hell starts being (let (( ?

Let is a "function" that lets you make intern variables, those variables won't escape from let body.

First part of let is expecting variables declarations/definitions, and the second one is expecting sentences to work with those variables.

In a much clearer way we could indent let as we were C coders:

( let
(
(oh 3)
)

(+ oh 2)

)


But lispers will kill us for doing such thing...

So we will hide us when doing those things in order to still alive, and in front of lispers we will indent like they want.

Also C indentation it's just for clear things, once you got where parenthesis go, you'll have no problem with lisper indentation.

So (let ((oh 2) (meh 4)) (+ oh 3) (+ oh meh)) should be clear for you now...

If not, we will make lispers hate us and perform our offending C indentation.

( let
(
( oh 2 )
( meh 4 )
)

(+ oh 3)
(+ oh meh)
)


Isn't it clearer? Well, don't do that if you want to live, because lispers will burn your house and kill your family for doing such evil thing.

When I started programming, I did not any indentation, and people who saw my code cried and suffered.

But with the time I got used to indent my code and it was nicer to look at it.

I really think if lispers were following a good indentation, more newcomers would like the language, but I cannot understand the reason they don't care about clear code. For them it's clearer with lisper indentation.

So why no one knows about Lisp? This is fault to lisp conventions, to do not indentate properly...

If you are a lisper, you got used to lisper indentation, so you have no problem with this kind of indentation. Also you want newcomers to follow those rules.

I don't see the point of this.

Indentation helps to convey a better structure of a program to the readers
It is used to clarify the link between control flow constructs such as conditions or loops, and code contained within and outside of them.

Why lispers don't want to indent "properly" their code?

Because they use a program to match the parenthesis, so they don't need to track them.

So, for working with lisp you "must" have something that helps you to count parenthesis.

This means, no vi, and no plain text editors. Also the recommended environment is emacs with slime.

I like to use vi... What lispers say about?

- Fuck you, you must use emacs and follow our conventions if you want to be a lisper.

So I need to use emacs, just because it's a convention to do not indent properly?

WTF

If you state that C indentation is better than the Lisp one, they'll don't care about your useless arguments.

Of course, every language has it's own conventions, and if you want to contribute to this community you need to follow their rules.

But I still thinking that it's a lot cleaner the other way.


" What is clearer "
( let
(
( variable1 30 )
( variable2 10 )
( variable3 20 )
)
(values
( + variable1 30 )
( + variable2 50 )
( + variable3 10 )
)
)

"or..."

(let ((variable1 30) (variable2 10) (variable3 20)) (values (+ variable1 30) (+ variable2 50) (+ variable3 10)))



If you state this in front of a lisper no matter how you say it, he will throw your arguments saying that conventions are made for some reason.

The reason I see is to scare people and don't let newcomers see the power of lisp. If that's not the reason, at least it's the consequence.

So now we have the answer of "Why no one knows Lisp"

I like the first indentation much more than the second one, even knowing that the second one is just one line.

It remembers me like when I started and did not any kind of indentation. It really makes me think that they don't want let you learn lisp. But I want let you learn lisp, because it's a very nice language, different than the other ones.

And now you saw that it's not fault of Lisp syntax. With my shit indentation you can see the parenthesis now have their logic.

Also this kind of indentation it's not forcing me to use any IDE or editor matching any parenthesis or doing auto indentation, which is nice, because I understand emacs is a very nice editor and it has a lot of cool things, but I don't want to loose my time learning it. Also I won't use emacs just because people say I need to follow non-sense conventions.

We can even make a function named "reduce-hate" which will be able to parse our evil indentation to the lisper one.

Well, once I've gained the hate of all lispers in the world, we can start learning a bit of Lisp, but mostly why it's a nice language.

Why Lisp is so nice ?



Lisp is a multiparadigm language, it supports:

- Functional programming

In functional code, the output value of a function depends only on the arguments that are passed to the function, so calling a function f twice with the same value for an argument x produces the same result f(x) each time.

This is in contrast to procedures depending on a local or global state, which may produce different results at different times when called with the same arguments but a different program state.

Eliminating side effects, i.e., changes in state that do not depend on the function inputs, can make it much easier to understand and predict the behavior of a program, which is one of the key motivations for the development of functional programming.

Functional programming has its origins in lambda calculus, a formal system developed in the 1930s to investigate computability, the Entscheidungsproblem, function definition, function application, and recursion.

Many functional programming languages can be viewed as elaborations on the lambda calculus.

- Object oriented programming

Object-oriented programming (OOP) is a programming paradigm based on the concept of "objects", which may contain data, in the form of fields, often known as attributes; and code, in the form of procedures, often known as methods.

A feature of objects is that an object's procedures can access and often modify the data fields of the object with which they are associated (objects have a notion of "this" or "self").

In OOP, computer programs are designed by making them out of objects that interact with one another.

There is significant diversity of OOP languages, but the most popular ones are class-based, meaning that objects are instances of classes, which typically also determine their type.


- Metaprogramming

Metaprogramming is a programming technique in which computer programs have the ability to treat programs as their data. It means that a program can be designed to read, generate, analyse or transform other programs, and even modify itself while running.

Metaprogramming can be used to move computations from run-time to compile-time, to generate code using compile time computations, and to enable self-modifying code.

The language in which the metaprogram is written is called the metalanguage. The language of the programs that are manipulated is called the attribute-oriented programming language.

- Reflective programming

The ability of a programming language to be its own metalanguage is called reflection or "reflexivity"

Reflection is a valuable language feature to facilitate metaprogramming.

Reflection is the ability of a computer program to examine, introspect, and modify its own structure and behavior at runtime.

Reflection helps programmers make generic software libraries to display data, process different formats of data, perform serialization or deserialization of data for communication, or do bundling and unbundling of data for containers or bursts of communication.


- Procedural programming

Procedural programming is a programming paradigm, derived from structured programming, based upon the concept of the procedure call. Procedures, also known as routines, subroutines, or functions, simply contain a series of computational steps to be carried out.

Any given procedure might be called at any point during a program's execution, including by other procedures or itself.

The first major procedural programming languages first appeared circa 1960, including Fortran, ALGOL, COBOL and BASIC Pascal and C.


There are more paradigms Lisp is able to perform, and due to it's mutable nature you can add any paradigm you want in an easier way than with other languages.

Sorry if the descriptions of paradigms are shit for you, if you want to blame, blame to wikipedia ( Yes I've copypasted it )

So knowing that Lisp really lets you use whatever style you want, isn't it a nice feature?

Also for example, I'm interested in Metaprogramming. I've learned a bit of lex and yacc and I've found it's very useful.

I guess Lisp can work much better doing the job of lex and yacc.

So why we should learn to use such a language?

You need to learn it first and survive to the parenthesis attacks in order to understand and see why Lisp is so good.

One of it's major and distinguishable features are macros. Macros create code on the fly and let you modify Lisp behavior.

But it's to soon to get a look on macros, and they're not the only feature of Lisp.

It has a lot of useful built-in functions and the fact it works with lists as a base "data type" it's really a nice feature.

If you worked with C, make lists is a pain compared with other languages. Malloc disarms your compiler warns and is an open door for bugs and segfaults.

If you work with Lisp, the first thing you learn is to create lists.

Also, because Lisp ( LISt Processing ) works with lists as a base, it has a lot of "functions" to work with lists.

For example mapcar

Mapcar is a nice built-in function that takes a list and a function. Then mapcar calls this function for every member of this list.

So what it does is to take the list, take the first member and pass it as an argument for the function, then it takes the second member of the list and passes it as an argument of the function, and so on until the list is empty.


mapcar #'function list


Why we see this #' strange character combination, is because it's like we are passing the pointer of this function.
The mapcar function will call our function all the times it finds a member of this list, until it reaches the end.

A usual example when learning lisp, is to show it with the "predicates" evenp and oddp.

evenp and oddp are built-in functions in lisp. They return nil (false) or true, depending of whether the number is even or odd.

So:

(evenp 3) ;; This will be nil (false)
(oddp 3) ;; This will be true
(evenp 2) ;; This will be true
(oddp 2) ;; This will be false


Of course this is a shit function, and it's not doing any interesting thing.

But they'll serve as an example for mapcar


(mapcar #'evenp `( 1 2 3 4 5 6 7 8 9 10))
;; result will be NIL T NIL T NIL T NIL T NIL T
(mapcar #'oddp `( 1 2 3 4 5 6 7 8 9 10))
;; result will be T NIL T NIL T NIL T NIL T NIL


The reason why we see a backquote is because backquote in lisp makes the list act as Data, not code.

Another use of mapcar should be using the "list" function, which creates a list.


(mapcar #'evenp (list 1 2 3 4 5 6 7 8 9 10))


Of course, using evenp or oddp we are doing nothing, but mapcar accepts any function, even our own ones.

So it's nice to see that we have a function able to call our function for every member of the list and we don't need to care about iterating the list and checking if it's null.

Try to create a function like mapcar in C and you'll see it's a pain.

Also if we didn't have mapcar in lisp, It won't be difficult to create it, just because lists are a natural thing for this language.