Hacker Newsnew | past | comments | ask | show | jobs | submitlogin

> Handles have many nice properties, for example you use them to easily implement promises.

Confused, (how) is this different from pointers?



Handles in the general way are an opaque reference that can be resolved into a pointer.

Index into an array is only one of the multiples implementations.

It can also be a hashed key or even contains directly a pointer

Because handles are weak references they can be used as promises, returned immediately but resolvable only when the the actual work is done.


But all of these are true for pointers too? Preallocate memory, return a pointer to it, lazily fill in parts later. You're already doing that with a handle anyway, whether it's indexing into array memory or something else.


You can't always pre-allocate and the pointer is not giving you much information about the availability of the data behind it.


As I see it, this just isn't true. I think you're going to have to elaborate on this with an actual concrete example (i.e. code) if you'd like to make a convincing argument.


"pointer is not giving you much information about the availability of the data behind it"

"elaborate on this with an actual concrete example"

The pointer may get invalidated, for example by reallocation of the underlying data structure:

    #include <iostream>
    #include <vector>

    struct ItemPrinter
    {
        int* ptr;
        void print()
        {
            std::cout << (*ptr) << std::endl;
        };
    };

    int main()
    {
        std::vector<int> items{1};
        ItemPrinter foo{&(items[0])};
        while(items.size()<1000)
        {
            foo.print();
            items.push_back(2);
        }
    }
When push_back exceeds the vector capacity, it needs to reallocate and `foo.ptr` gets invalidated.

Output when executed via http://cpp.sh/

  1
  0
  1
  1
  35557904
  35557904


You'll have to wait until I publish my article on this subject if you want to see some code.

But can you agree that a pointer does not give you anything else than a direct reference to a memory area?

Because of the indirection, a handle can do much more, depending on the implementation.


> But can you agree that a pointer does not give you anything else than a direct reference to a memory area?

Depends what you mean. Not if I take it literally, given you can generally shove a few extra bits into pointers. But in a sense it's approximately true.

> Because of the indirection, a handle can do much more, depending on the implementation.

Not unless you're playing semantics with what "handle" means. I'm going on the assumption that we can assume it's an opaque reference of equal size as a pointer to data that is or will be in the machine's user-mode memory. If that's not what you mean, then this is a seriously pointless argument, given you can obviously define "handles" to anything (even data on another machine) where nobody in their right mind would be arguing you could just replace it with a pointer...

Again, this is why you really need to provide examples to make a convincing argument (and you really can't expect people to wait for you to publish an article if you're going to bring it up beforehand). So we don't end up arguing over something that turns out to be pointless.


> I'm going on the assumption that we can assume it's an opaque reference of equal size as a pointer to data that is or will be in the machine's user-mode memory.

If the handle is an array index or a hash, it can be much smaller than a pointer. 8 bits in extreme cases, often 16 bits (if there's only a few thousands objects of that type), and we almost never ever need more than 32 bits.

Such handles can easily have less memory overhead than actual pointers, even after accounting for the redundancies needed for some runtime checks.


If you shove a few extra bits into a pointer, then it can't directly be used to dereference something. In practice it would be what I call an immediate handle (a handle that can be resolved to a pointer with a test and simple bitmask)

void* ResolveHandle(handle h); this is the basic API, and it will return nullptr if this handle is not allocated or has been freed. Or it will block if this handle is a promise. The handle itself can be an index, but also the hash of a string, the string being a path to a ressource that is not even loaded yet.


> If you shove a few extra bits into a pointer, then it can't directly be used to dereference something. In practice it would be what I call an immediate handle (a handle that can be resolved to a pointer with a test and simple bitmask)

That's just a smart pointer. Unlike a handle, it's anything but opaque. (And in your comment you specifically lumped smart pointers under "pointers" too, so we should be in agreement.)

> void* ResolveHandle(handle h); this is the basic API, and it will return nullptr if this handle is not allocated or has been freed. Or it will block if this handle is a promise.

Again, there's nothing preventing you from making a smart pointer that does exactly what you're talking about here, which (again) both of us would lump under "pointer".

Perhaps worth elaborating on: The concepts of handles and pointers, as I'm talking about them at least, are fairly language-agnostic. What makes a handle a "handle" to me (and I would've thought to you too) isn't the wrapper around it; it's the opaqueness. Not from a mechanical sense (i.e. not the public vs. private or the language syntax, which aren't even relevant in every language) but from an informational sense: whether it can be "dereferenced" without additional information.


I haven't read the whole article yet but it says pretty early on that they're indexes to an array




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: