FAQ
If you want simple short stacks or queues in Go, why not just use a slice
and be done with it?

That was my first impulse, but slices (that have reached capacity) get
copied every time you append an item, right?

I'm going to have lots of queues and some will have (much) more heavy
traffic than others - I don't want to waste memory by making room for 100
items in thousands of queues when 90% of those will have 1-3 items at a
time before getting flushed. And I definitely do not want lengthy code
(such as I saw written by a third party) that checks to see if the slice
has reached it's limit, reallocates and copies it to a new slice to double
it's capacity. (ideally that's what I need, but I don't want that code
replicated in every type.)

I'm pretty pleased with what I have now actually - I might revisit it at
some point and improve it, but for now, this does what I want, the
(consumer) code comes out nice and semantic, and it doesn't tax memory or
CPU too bad. Acceptable trade-offs. I can always come back and
optimize/replace some or all of this :-)

Also: pointers to pointers... I know this is totally common for people who
worked in C or C++ and it may seem like a ridiculous reason, but it makes
my head spin, and it was one of the main reasons C or C++ never caught on
for me personally. It's one of the reasons I like Go - I can think of
pointers as references, conceptually, and it "just works", without my
getting distracted by low-level technical thinking when I'm trying to solve
high-level problems.

That's actually the main attraction for me in Go - a language with concepts
that "just work" most of the time, with performance comparable to C or C++
but without all the distractions from low-level artifacts, which Go
successfully abstracts into usable high-level concepts. It makes me smile,
and at times even giggle - I haven't had that experience with another
language in many years :-)

Anyhow, I digress.... :-)



On Thu, Jan 2, 2014 at 10:31 AM, Thomas Bushnell, BSG
wrote:
On Sun, Dec 22, 2013 at 9:20 AM, Rasmus Schultz wrote:

Also, the queue I'm going to end up with is actually going to do other
and more complicated things than this - it was just a place to start. I
don't want to duplicate all of that functionality across several different
queue types. My first concern here is building a maintainable solution.
Computational performance is secondary.
In practical terms, it turns out that it's almost always easier to simply
write pop as you use it, rather than write a new function called "pop".

I recall learning some wisdom from the BSD kernel (maybe it pre-existed
them; dunno) in which large structs were on linked lists with a pair of
pointers thus:

struct foo {
...
struct foo *next, **prevp;
...
}

And then you delete f with *f->prevp = f->next. Since Go has real
pointers, the same thing works there, obviously with different syntax.

Note that this is one line, and once you know the idiom, just as easy to
read as "delete_foo_from_list(f)", and since a given struct can be on many
lists, it's simpler too than having a bunch of functions. Those functions
tend to accumulate extra stuff ("oh, why not manage this lock here, and do
some interrupt work and ...") which means you need to go look at them to
know exactly what they do anyhow.

If you want simple short stacks or queues in Go, why not just use a slice
and be done with it? It's not any more to write than a function call to Pop
and Push? If you want larger ones, why not just use pointers and be done
with it?

Thomas
--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.

Search Discussions

Discussion Posts

Previous

Follow ups

Related Discussions

People

Translate

site design / logo © 2022 Grokbase