Return Styles: Pseud0ch, Terminal, Valhalla, NES, Geocities, Blue Moon. Entire thread

Lisp BigO

Name: Anonymous 2012-01-02 16:07

How fast is:
 
(cdr list...)

Name: Anonymous 2012-01-02 16:15

O(1)

Name: Anonymous 2012-01-02 16:16

mov eax, [eax+3]

Name: Anonymous 2012-01-02 16:32

Are you familiar with a CONS CELL?

Name: Anonymous 2012-01-02 16:36

>>4
of course not

Name: Anonymous 2012-01-02 16:44

does lisp optimize for tail recursion?

Name: Anonymous 2012-01-02 16:50

>>3
U MENA mov 4(r0), r0

Name: Anonymous 2012-01-02 16:50

>>6
Scheme does. For CL it's upto the implementation. Every implementation worth using naturally does.

Name: Anonymous 2012-01-02 17:47

It's just a pointer de-reference. If this were C, it could be seen as list->cdr, where cdr could translate to some offset like +4. In x86 assembly it could look like:
mov reg1, [reg2+4] or lea reg1, [reg2+4].
Obviously O(1).

Name: >>9 2012-01-02 17:49

>>4
A cons cell is just a pair of 2 values, the car and the cdr, usually to be thought of a type-tagged structure of 2 elements (sometimes compressed into a register-sized object for extra performance).

Name: >>10 2012-01-02 17:50

s/>>4/>>5//

Name: Anonymous 2012-01-02 17:55

>>9
U MENA movl 4(r0), r1 or moval 4(r0), r1

Name: Anonymous 2012-01-02 17:58

>>10
so:

struct simple_con {
  void *car;
  void **cdr;
}

Name: Anonymous 2012-01-02 18:08

>>13

this could work:


struct simple_con {
  void *car;
  struct simple_cons *cdr;
};


although people sometimes put other things in the cdr, like numbers or strings.

Name: Anonymous 2012-01-02 18:14

>>14
struct simple_cons {
  union {
    struct simple_cons *car;
    intptr_t intcar;
  };
  union {
    struct simple_cons *cdr;
    intptr_t intcdr;
  };
};

If intptr_t and pointer to struct are the same size, this could work.

Name: Anonymous 2012-01-02 18:27

>>15

yeah, I should have clarified. In dynamic languages, primitives are often wrapped inside of tagged objects. So an int is actually something like:

struct fixnum {
  enum object_type = TYPE_FIXNUM;
  int value;
};

And then this object would be allocated on the heap, possibly using reference counting, or just depending on garbage collection. So in this case, storing a primitive in the cdr is just storing a pointer to something other than a cons cell. So it might be more accurate to just do:

struct simple_cons {
  void *car;
  void *cdr;
};

Name: Anonymous 2012-01-02 18:31

ENTERPRISE CONS


/*
 *  Cons.java
 *
 *  Copyright 1997 Massachusetts Institute of Technology.
 *  All Rights Reserved.
 *
 *  Author: Ora Lassila
 *
 *  $Id: Cons.java,v 1.2 1998/01/22 13:08:38 bmahe Exp $
 */

package org.w3c.tools.sexpr;

import java.io.PrintStream;
import java.util.Enumeration;

/**
 * Basic class for implementing linked lists a la Lisp.
 */
public class Cons implements SExpr {

  private Object car;
  private Object cdr;

  /**
   * Initializes a Cons cell with the left and right "subtrees".
   */
  public Cons(Object left, Object right)
  {
    this.car = left;
    this.cdr = right;
  }

  /**
   * Initializes a Cons cell with a left subtree only.
   * Right subtree will be set to <tt>null</tt>.
   */
  public Cons(Object left)
  {
    this.car = left;
    this.cdr = null;
  }

  /**
   * Returns the left subtree (i.e. the head) of a cons cell.
   */
  public Object left()
  {
    return car;
  }

  /**
   * Returns the right subtree (i.e. the tail) of a cons cell.
   */
  public Object right()
  {
    return cdr;
  }

  /**
   * Returns the tail of a cons cell if it is a list.
   * Signals an error otherwise (no dotted pairs allowed).
   *
   * @exception SExprParserException if the tail is not a Cons or <tt>null<tt>
   */
  public Cons rest()
    throws SExprParserException
  {
    Object r = right();
    if (r == null)
      return null;
    else if (r instanceof Cons)
      return (Cons)r;
    else
      throw new SExprParserException("No dotted pairs allowed");
  }

  /*
   * Returns an enumeration of the elements of the list.
   */
  public Enumeration elements()
  {
    return new ConsEnumeration(this);
  }

  public void printExpr(PrintStream stream)
  {
    printList(stream, true);
  }

  private void printList(PrintStream out, boolean first)
  {
    out.print(first ? "(" : " ");
    SimpleSExprStream.printExpr(left(), out);
    Object r = right();
    if (r == null)
      out.print(")");
    else if (r instanceof Cons)
      ((Cons)r).printList(out, false);
    else {
      out.print(". ");
      SimpleSExprStream.printExpr(r, out);
      out.print(")");
    }
  }

}

class ConsEnumeration implements Enumeration {

  private Cons current;

  public ConsEnumeration(Cons head)
  {
    this.current = head;
  }

  public boolean hasMoreElements()
  {
    return current != null;
  }

  public Object nextElement()
  {
    Object element = null;
    try {
      element = current.left();
      current = current.rest();
    }
    catch (SExprParserException e) {
      // current is a dotted pair
      current = null;
    }
    return element;
  }

}

Name: Anonymous 2012-01-02 18:33

>>16
No it isn't. You're still clueless. Cripes. Go scrub another toilet you fucking idiot.

Name: Anonymous 2012-01-02 18:38

>>18
yeah, I should have clarified. In dynamic languages, primitives are often wrapped inside of tagged objects. So an int can sometimes be implemented in the following manner

Name: Anonymous 2012-01-02 18:40

>>19
Please shut up, go leave this joint, and actually read a book. Instead of like, ya know, just picking up bits and pieces from google.

Name: >>10 2012-01-02 18:43

>>13
Both would be void*, although technically the inner details differ per implementation, saying that a cons has any properties than being a pair of 2 other objects (be they whatever you want, numbers, atoms, symbols, conses, structures, etc).
When you interpret/treat a cons as a list, then the car is supposed to be the first element (whatever that may be), and the cdr is supposed to be the rest of the list. A proper list terminates when cdr points to an object called '() or NIL or () (just a symbol named nil, nothing more; this applies for CL, for scheme it's only '()). An improper list does not follow the previous rule, examples could be circular lists or merely putting some other object than '() in the final cdr(after traversal). Improper lists tend to be printed like: (a . b) for (cons a b), while the proper list '(a b) could be generated (among other equivalent code) by (cons 'a (cons 'b nil)) (A side-note: I didn't quote nil because it's self-evaluating, that is, the value of nil is 'nil itself, same goes for t).
The closest I can think for how to write a cons-like thing would be:

tagged_struct cons
{
    LispObject car;
    LispObject cdr;
}

Where LispObject is some tagged object by itself, but its dimensions are to remain a mystery (until some implementation decides how it wants to handle it, but you could imagine it could use some 1-2 bits for type-tagging, thus you could end up with fixnum integers being encoded in a register-sized object, while some other object might be  a full pointer or(|)'d with a tag). tagged_struct is to be taken to be some other LispObject as well. Of course, since such implementations are messy to do in C in simple ways, despite being what most Lisp implementations do in practice(for performance reasons), you could always imagine something like:
struct cons
{
    enum uint tag = TAG_CONS;
    LispObject *car;
    LispObject *cdr;
}



>>14
That's coming close to looking like a list, but lists are just conventions in Lisp, they're not the only thing cons does, but then you also said so.

Name: Anonymous 2012-01-02 18:46

>>20
excuse me, but if you can provide an alternative implementation that can support constructs such as the following

a = "lol I'm a string!";
print(a);
a = 1337;
print(a);

without wrapping primitives inside of objects that have something like a type tag, or a vtable pointer, then I would like to see it. And you can't optimize it to something like:

print_string("lol I'm a string");
print_int(1337);

because knowing predicting the type of a will, in general, reduce to the halting problem.

Name: >>21 2012-01-02 18:46

Should check my writing before posting:
*saying that a cons has any properties than being a pair of 2 other objects (be they whatever you want, numbers, atoms, symbols, conses, structures, etc) would be wrong.
*enum tag = TAG_CONS

Name: Anonymous 2012-01-02 18:49

>>22

because knowing predicting the type of a will, in general, reduce to the halting problem.

No it doesn't. Also, what you just rattled about doesn't reduce to the halting problem you fucking clueless dweeb. Holy shit you're dumb. Please just shut up and actually read a fucking book.

Name: Anonymous 2012-01-02 18:56

>>22
Lisp isn't dynamically typed in that sense you're talking about. Each object is type-tagged and types are clear at all times. Dynamic typing means that you can assign any type to some variable. There is no type prediction at runtime, it's just trivial type dispatching (where relevant, see typecase in CL). Static languages where a variable can only have a single type just eliminate the need of a type-tag by either doing type inference or asking the user to provide the types for the compiler (which are still checked, if a compiler is worth its salt).

Name: Anonymous 2012-01-02 18:57

Suppose that we have a method of always inferring the type of a variable in a dynamic language. And suppose we would like to know if an algorithm, A will halt or not. We can construct a new algorithm, B

function B()
  if(halts(A))
    a = "lol, I'm a string"
  else
    a = 1337
  end
  print(a)
end

We use the method to find out what the type of a will be when it is printed. If a is a string, then A halts. If a is an int, then A will not halt.

Name: Anonymous 2012-01-02 18:58

>>26
Again, you have zero clue what you're talking about. Now tell me what you do for a living? Given the fact you seem totally clueless about what you're talking about, I'm willing to bet you do tech support at the very best.

Name: Anonymous 2012-01-02 19:02

>>27
*as to what*

Name: Anonymous 2012-01-02 19:04

>>26
Did anyone claim type inference for dynamicly typed languages? Compilers tend to do it for trivial cases, but of course it won't do it for any non-trivial cases. Also, a static language (like ML) could just solve this problem by making a's type like this: type string_or_int = S of string | B of int;;, no problem there, it's limited enough for type-inference, but not free enough for dynamic typing.

Name: Anonymous 2012-01-02 19:07

>>27

yeap, you're right, I did it the wrong way. Hold on...

Name: Anonymous 2012-01-02 19:09

>>30
No. The only thing you need to do is shut up.

Name: Anonymous 2012-01-02 19:10

>>29

mr >>27-san didn't like my example of wrapping primitives in tagged objects, so I was just suggesting that type inference is not possible in general. That proof is wrong though, let me try again...

Name: Anonymous 2012-01-02 19:11

>>27
No... he's right. By this time you guys are arguing about static type inference in a dynamically typed language, which is insane on its face, but >>26-kun isn't full of shit, just irrelevant.

Name: Anonymous 2012-01-02 19:12

>>32
And you still haven't told us what you do for a living. Given your subpar technical responses on here, again, I'm willing to bet you work some shit hourly general labor labor.

Name: >>32 2012-01-02 19:15

naw, wait, I think the proof is correct. >>27-san, what do you find wrong with the proof?

Name: kodak_gallery_programmer !!kCq+A64Losi56ze 2012-01-02 19:20

>>35
He missed two cases,

Name: Anonymous 2012-01-02 19:24

>>36
I must know...

Name: Anonymous 2012-01-02 19:25

>>26
Suppose that we have a method of always inferring the value of a variable in a static language. And suppose we would like to know if an algorithm, A will halt or not. We can construct a new algorithm, B

function B()
  if(halts(A))
    a = 1
  else
    a = 0
  end
  print(a)
end

We use the method to find out what the value of a will be when it is printed. If a is 1, then A halts. If a is 0, then A will not halt.

Name: Anonymous 2012-01-02 19:28

>>29
Heh, the ML solution involves type tags anyway.

Name: kodak_gallery_programmer !!kCq+A64Losi56ze 2012-01-02 19:29

>>37
You need the additional case(s) because it's proof by contradiction. However, the minimum wage dipshit that posted the proof only supplies a really sloppy version of one case.

Newer Posts
Don't change these.
Name: Email:
Entire Thread Thread List