> Sort of. You can create a macro with defmacro, which like a special
> form controls the evaluation of its arguments instead of the arguments
> being evaluated first and the function only getting the results.
> Things like -> and defn are macros:

That means, the difference of composite form and special form, is the
order / sequence of evaluation of arguments? right?
Composite form can be a function(list) or some other supported data
structures(Vector, map and set). Special form which looks a lot like a
funciton, is NOT a funciton / list / composite form at all.

This also means, what is written on the book about special form
"Special forms are a particular type of composite form. For most
purposes, they are used very similarly to
a function call. The difference is that the first form of a special
form is not a function defined
somewhere, but a special system form that’s built into Clojure."

is badly written or wrong, right?

Its not about being special form as a composite form, they are
different to begin with.
Its not about being 'built into clojure', its about how they work.

> 5. (foo bar baz) with foo not a special operator: the subform foo is
> looked up at compile time and if it's a macro, macro expansion is
> performed. The transformed code is then evaluated per these rules.

I didn't understand this one.Is it about user defined function?

> 6. (foo bar baz) with foo not a special operator or a macro. At
> compile time, code is generated to evaluate foo, bar, and baz at
> runtime and then apply foo as a function to the arguments bar and baz.

I didn't understand this point too. An example would help.

> (def bar baz)   bar var interned              baz eval'd, bar set
> (macro x y)     macro is expanded             expansion is eval'd

Arn't they same? def is written withing clojure and when needed its
expanded.

> 'def is definitely a symbol.

If def is a symbol then it should evaluated to somthing?like, when I
write 'print' and press return key, I get

#<core$print clojure.core$print@4b455d1c>

but, in case of def, i get the following 'Error',

#<CompilerException java.lang.Exception: Unable to resolve symbol: def
in this context (NO_SOURCE_FILE:0)>

Isn't this concludes def is not a symbol cause its returning an error.




>From you explanation what i got that, built in macros are called
special form and I can also create my custom macros, which will be
called special forms. is it right?

Your second post is a little over my head :s


On May 26, 8:58 am, Ken Wesson <kwess...@gmail.com> wrote:
> On Wed, May 25, 2011 at 10:15 PM, iamcreasy <quazir...@gmail.com> wrote:
> > 1st question,
> > Is the form word is a typo here? Isn't the word will be item? If not,
> > is def a form? That means, this code contains 3 forms. :-s
>
> Technically, anything that can be evaluated is a form. A composite
> form is something like a literal list, vector, set, or map. The
> literal list case is treated as an operator and arguments; the other
> three just evaluate to vectors, sets, or maps, respectively, whose
> members are the evaluations of the nested forms, so:
>
> +                  => the + function
> (+ 1 2)            => 3
> [+ 1 2]            => a vector of the + function, 1, and 2.
> [(+ 1 2)]          => [3]
> #{(+ 1 2) 4}       => #{3 4}
> {:a (+ 1 2)}       => {:a 3}
>
> > 2nd question,
> > Is a composite form is a special form only when, the first item of a
> > list is something that is only predefined withing Clojure? If yes,
> > then is it possible to create custom special form?
>
> Sort of. You can create a macro with defmacro, which like a special
> form controls the evaluation of its arguments instead of the arguments
> being evaluated first and the function only getting the results.
> Things like -> and defn are macros:
>
> (-> 3
>   (+ 1)
>   (* 2))
>
> adds 1 to 3, then doubles, yielding 8. This couldn't work with a
> function, as it would get arguments 3, 1, and 2 as (+ 1) would
> evaluate, first, to 1, and (* 2) to 2. It wouldn't know what to do
> with 3, 1, or 2 -- whether to add 1 and then multiply by 2, or
> subtract 1 and then add 2, or what. The macro, however, operates on
> the *forms* and gets 3, (+ 1), and (* 2) and combines the first two
> into (+ 3 1) and that and the third into (* (+ 3 1) 2) by inserting
> each form into the next one after the operator and before everything
> else.
>
> (defn foo [a b] (+ (* a a) (* b b)))
>
> also cannot be a normal function call. If it were there would be
> several errors: foo undefined (most likely), also a and b undefined,
> so the first argument foo could not be evaluated, nor could the second
> [a b], nor could the third (+ (* a a) (* b b)). But instead it works
> to generate a function definition. It's a macro that expands to a (def
> ...) form, in fact.
>
> > But, at the beginning the writer said, there are four basic varieties
> > of forms.
>
> > 1. Literal,
> > 2. Symbol,
> > 3. Composite form and
> > 4. Special form.
>
> I'd say it's a bit more complicated than that. We have six things that
> are evaluated somewhat differently:
>
> 1. nil, true, false, numbers, strings, regexps, keywords ... evaluate
> to themselves.
>
> 2. symbols are looked up when evaluated to find a local or global var
> value they evaluate to.
>
> 3. Set, vector, and map literals have subforms evaluated, then
> evaluate to a set, vector, or map with the subforms replaced by their
> evaluated values.
>
> 4. (foo bar baz), if foo is a special operator like def, is a special
> form and is evaluated according to the built-in rules for that form.
>
> 5. (foo bar baz) with foo not a special operator: the subform foo is
> looked up at compile time and if it's a macro, macro expansion is
> performed. The transformed code is then evaluated per these rules.
>
> 6. (foo bar baz) with foo not a special operator or a macro. At
> compile time, code is generated to evaluate foo, bar, and baz at
> runtime and then apply foo as a function to the arguments bar and baz.
>
> The latter three can, of course, have zero or more arguments, not just
> two, and generalize appropriately.
>
> Different things happen at compile and run time in each case:
>
> Thing           Compile                       Run
> literal         inserted into bytecode        recalled from memory
> symbol          var resolved, deref compiled  var is deref'd
> (def bar baz)   bar var interned              baz eval'd, bar set
> (macro x y)     macro is expanded             expansion is eval'd
> (func bar baz)  fn-calling code compiled      func called with args
>
> For special forms other than def, the behavior varies; (if bar baz
> quux) for example compiles to a conditional test and branch and at run
> time bar is eval'd, then the test and possibly the branch occurs, and
> either baz or quux is eval'd.
>
> > According to the definition of Symbols from the book, its not a
> > symbol.
>
> 'def is definitely a symbol. (No pun intended.) However (def ...) is
> recognized as a special form by the compiler. Note that:
>
> def                symbol
> (def ...)          special form
>
> You can actually create variables named def and the like. If you
> reference them in other than operator position, it works:
>
> => (defn def [x] (+ x 2))
> #'user/def
> => (map def [1 2 3 4 5])
> (3 4 5 6 7)
>
> In operator position, though, you get the special form unless you
> qualify the name:
>
> => (def quux 42)
> #'user/quux
> => (user/def quux)
> 44
>
> If you define it locally, you can't use it in operator position at
> all, unless you rename it:
>
> => (let [def (fn [x y] (+ x y 2))
>          a def]
>      (println (def foo 42))
>      (println (a foo 42)))
> #'user/foo
> 86
> nil
>
> The second let binding gives the local def another name, a, that can
> be used to invoke it. It ends up using the foo that was def'd the line
> before as one of its arguments. The same thing can be used if a
> function argument or a loop binding is named def, and for any other
> special operator's name besides def.
>
> But although it can be done it is generally best to avoid naming any
> variable with the name of a special form, and especially any function,
> or anything you might want to call like a function, such as a map or a
> keyword.
>
> You also can't use 'nil, 'true, or 'false as names this way, or at all
> easily. The reader turns "nil", "true", and "false" into literal nil,
> true, and false objects, not symbols:
>
> => (def nil 42)
> #<CompilerException java.lang.Exception: First argument to def must be
> a Symbol (NO_SOURCE_FILE:1)>
>
> You can work around that by using eval when you need the name
> unqualified, but please just pick some other name instead:
>
> => (eval `(def ~(symbol "nil") 42))
> #'user/nil
>
> You can use it qualified without difficulty:
>
> => user/nil
> 42
>
> --
> Protege: What is this seething mass of parentheses?!
> Master: Your father's Lisp REPL. This is the language of a true
> hacker. Not as clumsy or random as C++; a language for a more
> civilized age.

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Reply via email to