Simon blogs

Started by Simon, October 18, 2015, 06:05:44 AM

Previous topic - Next topic

0 Members and 1 Guest are viewing this topic.

Simon



Tonight, I took the time to make this lovely gif of angry Colonel Shuffle. It's cropped sensibly and contains the maximum possible length of the shot without other stuff getting in the image.

Youtube: Source video (40 seconds)
Excerpt from Mississippi Hare, Bugs Bunny cheats Colonel Shuffle at Poker. Classic comedy.

There is even a bonus story here. Why did I think of this steamy cartoon scene today? Two weeks ago, I bought a new 49-inch monitor for home office. It works perfectly. Thus, it was time to dispose the packaging: A huge cardboard box and two gigantic pieces of polystyrene. They were too big for normal garbage, so I stuffed them in the car and drove to the recycling plant. The weather was surprisingly hot, I got into a traffic jam, and the car navigation didn't know the plant's street. I was about to run out of time before the plant closed for the day. I took half a day off work for this? I had to call Icho in the middle of the traffic jam to look online for nearby streets, in hope to enter one of them into the navigation system.

-- Simon

mobius

#286
Quote from: Simon on March 26, 2021, 06:39:52 PM
I had to call Icho in the middle of the traffic jam to look online for nearby streets, in hope to enter one of them into the navigation system.

Somehow this doesn't surprise me. And I'm certain he knew exactly where you needed to go without researching :P :D
great gif btw, I remember that one from my childhood! :lix-cool:
everything by me: https://www.lemmingsforums.net/index.php?topic=5982.msg96035#msg96035

"Not knowing how near the truth is, we seek it far away."
-Hakuin Ekaku

"I have seen a heap of trouble in my life, and most of it has never come to pass" - Mark Twain


Simon

#287
Thanks! No, this time, Icho had to research. I've moved to nearby town last year, and neither of us knew that plant in the middle of nowhere.






Amount estimation

You have n people. You want to cook dinner/rice/noodles/... and ensure to cook enough for all n.

Let's assume that when we, as a single person, are really hungry, we eat y noodles. Should we cook ny noodles for the entire group? No, that's too much. The chance that everybody is super hungry is small. For a single person, you'll certainly want to cook y noodles. But for 4 people, 3y noodles will probably suffice. For 5 people, 3.5 y. If you have women in the group, even more reason to cook less per person than y.

Linear models of the maximum for safety estimation won't scale when probability is involved. You'll want to model the average and scale that linearly. (Plus a safety amount that grows logarithmically.) But the average, as natural as it sounds, it can be surprisingly hard to reason about it. It's often much easier to think of an extreme case -- certainly, 1-2 people of the 10 invited will be extremely hungry -- and that is wise, and then linearly extrapolate to 10 people after forgetting that we're really extrapolating a statistical maximum for one person, and that is wrong.

The converse principle applies when you scale down: Let's assume you've heard that 100 people need Y noodles. Then, for 10 people, cooking 0.1 Y would be too little. You'll want to cook 0.15 Y.

-- Simon

Simon

#288
4 spaces

Indenting code with anything less than 4 spaces is claustrophobic. 4 spaces is good.

Example of bad is Google's C++ style that indents with 2. Why not 1 then? Doesn't make a difference much anymore in clarity.

The alleged exception is Scala -- the language, and even more the culture around the language. They favor nested expressions, not only nested compound statements. Likely, Scala writers indent carefully even within a single expression, and then make long expressions?

Several times already, I've toyed with the thought to make Scala the next language to learn. Allegedly, its type system has elegant solutions to solve common problems, often different to what was considered the solution in academics. Nnnnnnnn... but do I really want to chain the JVM permanently to whatever project it will be...




Nesting within a single expression will happen in many languages, but it hasn't yet been a reason for me to reject 4-space indentation.

Example from my D
You have a function onExecute() that takes a function for its 3rd argument, and you pass a lambda (function literal) that contains statement nesting or more such function nesting. Then you quickly get an indentation depth of, e.g., 5 like in the following, even though there is only one nesting statement, with, in the top-level makePanel().

void makePanel(Editor editor)
{
    editor._panel = new EditorPanel();
    addDrawingOnlyElder(editor._panel);
    with (editor._panel) {
        onExecute(
            Lang.editorButtonFileNew,
            KeySet(),
            () {
                editor.askForDataLossThenExecute(() {
                    editor.setLevelAndCreateUndoStack(newEmptyLevel, null);
                });
            }
        );
        // ...
    }
}


And we still stay within 80 characters per line despite indentation depth 5, indentation with 4 spaces, and long function names.

-- Simon

Simon

Hice

One mouse, two mice.
One house, two hice.
Very nice.




More seriosly, to hammer it in stone: I want to adhere to an early daily rhythm. All times are local times, i.e., UTC+2 in Summer, UTC+1 in winter.
  • 05:00: Rise. Minimal physical excercise. Shower. Dress. Take morning walk.
  • 06:00: The bakery opens. Buy Brötchen, return home, eat breakfast.
  • 07:00: Start work.
  • 16:00: End work if the day was normal, otherwise continue working.
  • 20:00: End of private computer usage. Offline hobbies, household, or early bed.
  • 21:00: Go to bed, maybe some reading, but not for hours.
Exceptions are OK for Lix sessions or other social things with a group of people who don't adhere to early rhythms. The schedule provides 8 hours of sleep, it's usually okay to compress it to 7 or 6 hours for a day, but it should never get out of hand.

Ending computer usage an hour before bedtime is common advice, see earlier posts by me/geoo on sleeping problems.

Good night!

-- Simon

WillLem

Regarding coding, the thing I find most difficult to get used to is everything being in curly braces and with different indentations.

By the time you have something like this:


void makePanel(Editor editor)
{
    editor._panel = new EditorPanel();
    addDrawingOnlyElder(editor._panel);
    with (editor._panel) {
        onExecute(
            Lang.editorButtonFileNew,
            KeySet(),
            () {
                editor.askForDataLossThenExecute(() {
                    editor.setLevelAndCreateUndoStack(newEmptyLevel, null);
                });
            }
        );
        // ...
    }
}



I have no idea which set of curly braces goes together, it's so easy to lose track. I'd prefer a language that is more like this:

function A = (description of function)
function B = (description of function)
function C = (description of function)
condition D = (description of condition)
condition E = (description of condition)

1. Do A
2. Do B
3. Do C, unless D, in which case do A again
4. Do B again, but only iff E

Dullstar

#291
In most (if not all) languages with curly braces, the indentation doesn't actually matter - it's just a formatting tool to make it easier to follow the braces.

I think I've mentioned this to you before in the Discord, but Python is a very good starter language. Its syntax is easy to follow. The indentation is enforced in Python, and once you understand it adding the curly braces in languages that have them is easy. It's also rather practical - people actually use it to do real tasks; it's not just a language that was designed specifically for people to learn off of before moving on to something else. It is a bit slow relative to C, C++, D, C#, Java, etc., but for a lot of tasks it's not slow enough to be an issue. In Python, your example would look something like this:



def A():
    # Do stuff

def B():
    # Do stuff

def C():
    # Do stuff

A()
B()
if not D:
    C()
else:
    A()
if E:
    B()



Note that this won't actually run, though, because the functions don't actually have anything in them, and that's not allowed: any time an indented block is expected, it has to be filled in with something, and comments don't count. There is a "pass" statement that can be used that can be inserted where the program is doing nothing, but a statement is syntactically required, however.


EDIT: Note that I never actually defined D and E. If they're simple conditions, e.g. my_variable < 2, it would make the most sense to just inline them instead of defining it ahead of time, e.g.
if my_variable < 2:
    do_stuff()


However, if it were a more complicated condition, you could make a function that evaluates it and returns either true or false, then call that inside of if statements:
def D():
    # Some long and complicated calculation here
    return result  # result is either True or False

if D():
    do_stuff()

Simon

#292
The chunk in Python would look like this:

def makePanel(editor: Editor) -> None:
    editor._panel = EditorPanel()
    addDrawingOnlyElder(editor._panel)
    with editor._panel as p:
        p.onExecute(
            Lang.editorButtonFileNew,
            KeySet(),
            lambda: editor.askForDataLossThenExecute(
                lambda: editor.setLevelAndCreateUndoStack(newEmptyLevel(), None))
        )

Readability is roughly the same? Maybe indeed a tad better without the closing brace forest.

Sidetrack: Python "with"
The D with statement makes an object implicit within the scope; i.e., all calls of onExecute will be interpreted as editor._panel.onExecute. In the real code, there are several calls to onExecute, omitted with the // ... in the D chunk. Strictly, we don't need the with at all; it adds a nesting level to make the inside code less verbose.

The closest similar feature in Python is the Python with because that allows us to alias the to-be-implicit object as something short. That with will always call __exit__() on the object and _panel has no __exit__(). Thus, the chunk will crash because of the nonexistant method.

The Python with isn't for introducing shorthand, it's for safeguarding resources and ensuring that they're freed exactly once after the with scope.

But that's not the topic here; the topic is the nesting in the lambdas.

QuoteI have no idea which set of curly braces goes together, it's so easy to lose track. I'd prefer a language that is more like this:
[declare many smaller functions and nest less]

Right, this is the correct feeling. We shouldn't write long or deeply-nested functions, but rather put different parts of the logic in separate functions.

The nesting in this example is necessary because we must capture the local editor in an argument-less function. Thus the definition of the function must be in the same scope where the editor variable of interest exists, which cannot be global scope.

The UI button gets assigned an argument-less function. All the button knows to do is call the function whenever we press the button. The button doesn't know about Editors, and it shouldn't have to know about them. It receives an argument-less function that already contains all necessary extra information (in its "closure").

I didn't choose the example because deep nesting were good, or for showing that I can use all these language features together; deep nesting is indeed to be avoided in general.

I chose the example because even when deep nesting cannot be easily avoided, 4 spaces is OK as an indentation. Any other solution in this particular instance of the problem, e.g., capturing the extra information in Command pattern classes like I do for the undo feature, would be 3-5 times as long and touch unrelated Button code. Thus, I accept the deep nesting this time, as a deliberate tradeoff.

-- Simon

Simon

Culture

Image: Kvick Sört

Concise explanation of the fundamental idea, practically without words. Well, two uses of words, for the two recursive calls.

You can argue that it's too high-level, and you want lower-level algorithm that move the pivot element into place and shift the elements around (the partitioning step). This doesn't seem trivial to me if you insist on minimal complexity, i.e., I believe there is a chance that a naive implementation of the partitioning has higher-than-necessary complexity.

Youtube: Core Design Principles for Software Developers
by Venkat Subramaniam a.k.a. Hilarious Indian Scala Guy
2.5 hours, from 2015.

Warmly recommended to watch after you have a grounding in programming. Shows how software design principles (DRY, single responsibility, ...) apply in contemporary langauges that allow to mix object-oriented style, functional style, and metaprogramming.

High-level explanation of the ideas, often with stories as example. If there is code, it's mostly Java.

I recommended this to Arty in IRC 3 years ago, and it's still as good as ever.

-- Simon

WillLem

Quote from: Simon on May 13, 2021, 12:36:41 PM
Image: Kvick Sört
---
You can argue that it's too high-level, and you want lower-level algorithm that move the pivot element into place and shift the elements around (the partitioning step). This doesn't seem trivial to me if you insist on minimal complexity, i.e., I believe there is a chance that a naive implementation of the partitioning has higher-than-necessary complexity.

Interesting!

The algorithm itself is not complex at all, I think the only potential problem is that the steps must be repeated several times to reach the end goal. A more complex algorithm may sort the blocks more quickly (i.e. with fewer steps), so it seems to me that the simpler algorithm comes at the mere cost of higher repetitions.

Quote from: Simon on May 13, 2021, 12:36:41 PM
Youtube: Core Design Principles for Software Developers
by Venkat Subramaniam a.k.a. Hilarious Indian Scala Guy

Added this to my Java watch list :thumbsup:

Simon

I haven't stuck to the sleeping schedule that wakes at 05:00 local time. It's hard going to bed early enough when it's bright outside, and housework/stuff/... happens enough in the evenings. Maybe I'll get to it some day again.

Weight loss bet

I want to lose weight again. I'm weighing 89 kg at 1.91 m with mostly fat, little muscle. The goal weight is 80 kg until end of the year. The method is the proven guinea pig diet: Eat lots of cucumber, put lots cucumber on bread to make meals more elaborate to prepare, have lots of healthy veggies, and have fewer snacks. Light strength training with pushups, but nothing excessive.

Around December 20th to 24th, I'll weigh myself. For every 100 g above 78 kg, I will donate 1 euro to the hosting of Lemmings Forums. E.g., merely touching the goal weight of 80 kg is 20 euros. Being lazy and not losing weight at all is 110 euros.




-- Simon

Ramon

Back to cucumber diet? I vaguely remember having heard this from you before, or was it geoo? :P How about some more garlic in the pot?

Do you find 89 kg to be a lot for your height?

namida

QuoteFor every 100 g above 78 kg, I will donate 1 euro to the hosting of Lemmings Forums. E.g., merely touching the goal weight of 80 kg is 20 euros. Being lazy and not losing weight at all is 110 euros.

Take note everyone: The forums' survival is dependent on convincing Simon to eat lots of pizza. Not really, the site is fine, just in case anyone was actually worried.
My projects
2D Lemmings: NeoLemmix (engine) | Lemmings Plus Series (level packs) | Doomsday Lemmings (level pack)
3D Lemmings: Loap (engine) | L3DEdit (level / graphics editor) | L3DUtils (replay / etc utility) | Lemmings Plus 3D (level pack)
Non-Lemmings: Commander Keen: Galaxy Reimagined (a Commander Keen fangame)

WillLem


Simon

Thanks for the feedback.

Yes, 89 kg with barely any muscle is too much. 89 kg would be nice at 1.92 m weight were I to pack a punch!

Thumper is so happy about his pizza, I ordered burgers this past weekend because of him. It's probably okay to have one Thumper day per week if the others are all guinea pig days. Tomorrow, back to more veggies.

-- Simon