Register a SA Forums Account here!
JOINING THE SA FORUMS WILL REMOVE THIS BIG AD, THE ANNOYING UNDERLINED ADS, AND STUPID INTERSTITIAL ADS!!!

You can: log in, read the tech support FAQ, or request your lost password. This dumb message (and those ads) will appear on every screen until you register! Get rid of this crap by registering your own SA Forums Account and joining roughly 150,000 Goons, for the one-time price of $9.95! We charge money because it costs us money per month for bills, and since we don't believe in showing ads to our users, we try to make the money back through forum registrations.
 
  • Post
  • Reply
Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

candy for breakfast posted:

current coding horror is a new hire who wants to rename the production database because he doesn't like it.

i remember being young and wanting to rename things for no good reason. that's a lesson only experience can teach you.

Adbot
ADBOT LOVES YOU

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

duck monster posted:

When he was handed access to the TCP server (I'm being vague here, NDA. Its an end point for a IOT type thing) he was handed that whole project over from me so I could turn to other parts of the system. After an argument over his idiot plan to replace the old nodejs server with a PHP one (after he lied to the boss and told him nodejs cant do multitasking. like gently caress?) I just gave up and said "Fine, I want nothing to do with it" and the boss gave him the full keys to that one. That PHP replacement is a hot mess. All the SQL is via interpolated strings, the front end is a jquery horrorshow (He actually flew into a fit when he first started and wrote a full page rant about how he wanted our front end people to drop vuejs for jquery, and was soundly told to gently caress off and keep away)

He has no access to the two main clusters (data ingress , where the TCP server is sending info too and front end) because its a kubernetes system and I suspect he'd have no idea where to even begin with it. And in all honesty if he tried I suspect the boss would have a mutiny from the rest of the devs.

That said, I've been interviewing new developers for the team and have been carefully but covertly insisting on requirements that would let us drop in a replacement for this guy.

On the side I've been working with security on building a new set of security guidelines enforced by policy that he'll need to either adapt to or gently caress off. Mandatory code reviews, security linting to turn all those SQL injections into giant blaring sirens, etc, prohibiting uses of unprepared SQL as well as a policy that is phasing out PHP entirely so that everything is going to be using either lambda or kubernetes python architecture gated behind CI.

And this guy has proven himself almost violently unwilling to learn anything that isnt old school PHP

dude, i've fired people who would be 10x developers in comparison to this guy. have you had the "this dude may unironically have a learning disability or brain damage, I know you're concerned about an ada violation, but can you consider putting him on a project that will cause fewer problems" talk with your boss? the only times I've ever had problems as bad as this one involved developers who literally had part of their brain removed (brain cancer) / an addiction to painkillers, etc. and I got the real story just by being certain there is no way hosed up co-worker was working there on their own merit.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Jazerus posted:

sadly, many people emerged from the early 2000s with a terminal case of php & jquery brain yet it's not a recognized medical condition
many years ago i was a contributor to jquery. it actually sucks worse than all the people who hate it know (btw I hate it more than you guys do)

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Hammerite posted:

As a developer who works occasionally (but not specifically) on front-end stuff, I don't know what the connotations are of listing jquery on one's resume. Can you explain?

My vague impression of jQuery is that it was a major thing when it was first released over a decade ago, but that some of what it did is now part of the relevant standards so it may be a bit redundant now. Also that it's a toolbox, rather than a framework.
You could make the case for using jQuery back when browsers had to support both IE6 and chrome at the same time, because poo poo like event handlers worked differently in every browser. You shouldn't have been using it anymore in 2012, and even discussing it in 2022 is hilariously out of touch.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

cheetah7071 posted:

That kind of makes sense if you're American

Yeah but the language was not invented by Americans, so what the gently caress.

Bruegels Fuckbooks fucked around with this message at 17:56 on Sep 16, 2022

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Hammerite posted:

Spent half the afternoon tracking down a failure in a new deployment of an app (an engineering tool, not a customer-facing app) to a new version of a JS dependency. Well, should be no problem, right? Just stop it from pulling in the new version.

The person who originally created the app intended its dependencies to be maintained (or whatever is the term) using "yarn". They apparently took steps to pin dependency versions in the way "yarn" wants you to do things. Then someone later came along and added an automated deployment process using "npm" and something called "react-scripts". This thing is pulling in the latest version of the dependency despite the fact that there's an entry in "packages.json" telling it to use a specific version. Ok, internet says I need to take "package-lock.json", amend the version of the dependency and change the name to "npm-shrinkwrap.json", and it will use that exact version. Nope, somewhere along the way the deployment process overwrites "npm-shrinkwrap.json" and carries on using the latest version of the dependency. Look all over to figure out what it's doing, all I can find is that it is running "npm install", which Stack Overflow assures me respects "npm-shrinkwrap.json".

There's a command in npm, "npm explain", which is supposed to tell you why it's pulling in a particular version of a dependency, but it's only available in a later version than what's installed on the build server. and considering how loving flaky all these tools are I have no doubt that if I try to update the version on the build server I'll break everything for all the teams using it and get half a dozen people mad at me.

I do .NET languages, I shouldn't have to mess around with this stupid Javascript horseshit in the first place. Feeling about ready to do violence here.

it's job security for web developers. i've seen enough projects that only work if they use the one specific version of node.js that doesn't crash if you try to use a certain minifier etc. it's pretty dumb.

granted everyone who works in .net (at least back in my days as a .net developer) has googled something along the lines of "how do I get projects that use different versions of newtonsoft json to work together?" and learned a whole bunch of bullshit about binding redirects.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Hammerite posted:

I put it back to using Yarn and it's working now. Rage has subsided, the solemn intent to destroy all JavaScript has not.

I'm going to get a "gently caress javascript" tattoo somewhere just to make the interview process easier.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

SupSuper posted:

I didn't mean "write your own serializer", but "I can see the appeal in using a simple serializer for simple data", given half of .NET's serializers had to be deprecated for being a security issue: https://learn.microsoft.com/en-us/dotnet/standard/serialization/binaryformatter-security-guide

I worked on a project where were we needed a little performance in json serialization and deserialization and were like "gently caress reflection, let's just write the json serialization and deserialization by hand" and that poo poo worked just fine, performed well and we didn't have to patch the server when someone found out you could ddos a server using malicious json post requests.

When I was younger I reached for the library immediately every time - you'll see platitudes like "don't roll your own crypto", which isn't a BAD platitude, but I will say that in grad school, I used the SJCL for a crypto demonstration in one of my classes and actually found a bug in the library itself, and debugging that took an enormous amount of time to figure out, and I probably would've been better off rolling the crypto myself (probably not a typical experience, but it's always possible), so I'm becoming more and more sympathetic to the "not invented here, avoid libraries, gently caress it, write it yourself" crowd as I get older, even though they're often wrong. At the very least, having to using a library to do something should never make you happy.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Absurd Alhazred posted:

Has anyone had any experience with TypeScript? I've run into at least one software house which claims that it provides a lot of the benefits of a strongly typed language like C++ while still being able to run on the browser.

i've been using typescript since start of public release (about 10 years now)

a) typescript does make dealing with the javascript ecosystem much much better. i would never touch regular javascript in a project anymore, screw working with that.

b) typescript also works like helmets for football players in that the safety features end up being used to cause more grevious injuries. people used to throw out projects that were 100k loc javascript and actually make webapis because 100k of loc was considered too much for a front end, and now since it's easy to scale up a ts project, nobody cares, you end up with web pages that have literally 100+ mb of javascript framework, so this wonderful technology (typescript) has been used to enable some astoundingly braindead software.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

namlosh posted:

As someone who’s bounced off C and CPP for years and is now taking another shot at it in order to do some embedded dev, this part has caused me so many issues.
You think that it must be a problem in how you’re thinking about variables, addresses and pointers and it causes you to think you don’t “get it”
And for whatever reason, people don’t call it out. Like if I’m teaching CPP the first thing I’ll teach is this bullshit and how it’s dumb. * operator doing two totally different things like that is ridiculous. Wish I had realized it years ago and just accepted it and moved on lol.
I also think it’s stupid to try and teach pointers without teaching references hand in hand. Ughh

While I’m on a rant, c++ using << and >> operators in iostream in every tutorial is ridiculous. Like, let me put a super esoteric, advanced concept in front of people just learning the language. That won’t cause them to think it’s just magic lol

Arby’s drive thru… can I get extra horsey sauce please

like it's dumb but i've been writing c++ since the 90's so * doesn't even register among all the other dumb poo poo i see about the language.

c++ is one of the worst taught subjects in school to the point where it makes me suspicious of cs education in general. some people will just take c++ classes and think that they're any good at the language, or even literally put "c/c++" on their resume, when in reality you could literally write "gently caress you" on your resume as a joke and get a better reaction from me than if I see "c/c++" (and I mean literally "C/C++", it's reductive to group the two together and many C programmers would happily murder C++ programmers if given the opportunity, it'd be like putting "Israel/Palestine" as a line on your resume).

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.
I learned x86 assembly when I was at summer camp. The closest I got to writing a game was getting a square to wrap around the screen when you pressed the arrow keys. Inexplicably, I found assembly boring and was far more interested in playing the unreal tournament 99 beta. Not much has changed since then.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Missing "FileNotFound" and "{CompanyName}Yes"

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Macichne Leainig posted:

My favorite, the 4-state boolean.

This is why you model booleans as varchar in databases, so you can have

Y = Yes,
N = No,
Z = CompanyYes,
F= FileNotFound

etc.

Absolutely brilliant future-proofing.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

The only reason I could think of doing it this way is if you are perversely proud of this hack and want to get asked about it. It's software exhibitionism.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.
Let's just say I never claimed to be an expert in the physics of nuclear medicine.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Hammerite posted:

the post was pretty interesting, as someone who doesn't know much about how operating systems work at a low level. but the constant suggestion that one should have an emotional reaction to it was a bit irritating*. I mean all the "ye gods how awful it is that they are doing this! how gross! and now let me tell you about what they do with the file system" stuff. it's all just computer bullshit you don't have to try to make it juicy by talking about how it's the computer equivalent of HP lovecraft or something.

* the author of the piece is less guilty of this than all the commenters reacting to it

it's more that it's a high int low wis solution to a problem that probably took a significant amount of work to pull off. someone probably had the thought "hey, what if we just made each OS sleep and had them switch between the two" and then had the balls to keep going when they kept finding problems. doing the amount of work that they did to get this to work and getting a bad result (it's still loving slow to switch between the OS anyway) is a tragedy. i've dealt with engineers that can get anything to "work" given enough time and who would always double down on poo poo like this before and it's super frustrating working on a project that's fundamentally doing something that it shouldn't be doing.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

QuarkJets posted:

Yeah I guess I can see how some poindexters could get very mad at all of the rule-breaking going on

i'll give a more concrete example. Say someone wants a web service to print something for some godforsaken reason. Developer looks up the api and see something like "https://learn.microsoft.com/en-us/dotnet/api/system.printing?view=windowsdesktop-7.0." If you look through this, you'll note the following

quote:

Classes within the System.Printing namespace are not supported for use within a Windows service or ASP.NET application or service. Attempting to use these classes from within one of these application types may produce unexpected problems, such as diminished service performance and run-time exceptions.

There is a class of dev that will take this as a challenge and go ahead and write the code anyway. They give it to QA, it works. On actual deployment, it deadlocks because printer enumeration can throw a UAC prompt etc. etc.

Or, given a task to replace a context menu in a native application, they write 300,000 lines of code in three different languages involving keyboard and mouse hooks to intercept the windows context menu and open a browser window containing a context menu instead.

Like, I'd prefer people who are architecting systems to have a sense about what we should and should not do with a computer and I'd prefer that people would viscerally recoil at the examples I provided above rather than being like "let's have a three hour long meeting about why this is bad."

Bruegels Fuckbooks fucked around with this message at 22:01 on Mar 26, 2023

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

repiv posted:

https://twitter.com/gf_256/status/1640100620228083713

26 chromes on my machine totalling 2.8GB, i love modern software

man if only you could have a way of embedding a browser within an application without making a copy of the dlls. it's hilarious that we wasted all this time in the 90's on activex/com/ole and opendoc and the end result is "just buy bigger hard drives fucker".

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

abraham linksys posted:

microsoft is sort of trying to solve the packaged chromium on windows with WebView2, which will use system-installed Edge (so, Chromium) by default. applications can still choose to package a specific version if they're concerned about updates breaking the apps, though

teams is moving to it. i laughed very hard when i saw a headline saying "Teams Preview Ditches Electron!!" and thought "oh wow microsoft must have finally built a native UI framework they like enough to actually build software in it again" and no of course not they've just moved from Angular to React and Electron to WebView2 https://techcommunity.microsoft.com/t5/microsoft-teams-blog/microsoft-teams-advantages-of-the-new-architecture/ba-p/3775704

oh and naturally the internet is now filled with "how can i use webview2 from activex" and there are wrappers for it now. Imagine four balls on the edge of a cliff...

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Ranzear posted:

Bash is a good terminal but a miserable scripting language.

PowerShell is a good scripting language but a miserable terminal.

Trying to do both is the folly.

I think I would have been happier with "C# but you can pipe output into other commands easily" rather than actually have to read documentation about how to invoke functions in powershell because microsoft's manic pixy dream language is special and unique and doesn't invoke functions the way all the other languages do (with parenthesis like god intended).

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

JawnV6 posted:

I used to maintain perl written by EE's. EE's generally have funny ideas about software, will get things working once then move on to other problems. This was perl that smashed ASCII together into SQL queries, so just the best possible environment for clever solutions to persist for years.

A couple of the genius inventions that I had to deal with included
code:
$AND = "AND"
$OR  = "OR "
Thinking it was superfluous, I removed the extra space from $OR. Turns out it was load bearing, as it bashed strings together to make a SQL query it would get to the end and chop; chop; chop; to remove the "extra" operator, without the " " it would whack a ")" and imbalance things.

The other incredible move was redefining $\, the newline character, from '\n' to '' so it could slurp a whole file and do one s/// operation instead of "looping" over "lines" like some uncourageous jerk.

when maintaining feral perl you need to act as if it has a long term nuclear waste message around it, e.g.

quote:

This place is a message... and part of a system of messages... pay attention to it!
Sending this message was important to us. We considered ourselves to be a powerful culture.
This place is not a place of honor... no highly esteemed deed is commemorated here... nothing valued is here.
What is here was dangerous and repulsive to us. This message is a warning about danger.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.
322mb of registry entries strikes me as somewhat excessive for a single game.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Athas posted:

:godwinning: Yes, this is it. It's the kind of stuff that inevitably happens when you are building on top of a sufficiently complex tower of abstractions. It's likely the programmer didn't even realise anything was going in the registry.

I can forgive a programmer missing this but no one in their QA noticed this? It's a combination of "run your game long enough and game doesn't work anymore" and "dumps thousands of mb of keys in the registry" - that kind of bug is a QA wet dream.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

OddObserver posted:

Windows has ridiculously bad file system performance
Compared to what?

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Mind_Taker posted:

code:
public dynamic function(dynamic data) {
    int id = (int)(data.id);

....

    return some_string;
}
Stuff like this is everywhere in the codebase I'm reviewing for the job I just started.

this is what code from programmers who "don't like to be tied down to types" actually looks like in the wild. dynamic and the expandoobject have enabled some really bad c# code.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Ihmemies posted:

I have determined that our university’s webdev1 course is pure coding horror. Plain ES5/6 mixed haphazardly, mongodb, age old node packages. I tried to swim against the tide, using ES6 features like modules, and import/export, until a test in this week’s assignments banned them.

/home/user/study/tuni/webdev1proj/dist/models/user.js
I give up. I am making Internet Explorer compatible webpages with pure ECMASCRIPT 5 in TYOOL 2023. And I don’t have a choice if I want a grade from the course.

gently caress. gently caress this horseshit. 2nd largest uni in Finland btw, don’t come here to get your CS degree.

i'm 38, a principal engineer at a software company and have a master's degree in computer science and i literally never took a class that had javascript or any other form of webdev in the curriculum - every class i took at undergrad or grad level was in C++/C#/java.

i am a big fan of functional programming (which is also something that I didn't learn in college) but I feel that restricting for loops is getting lost in the sauce (unless the objection is that for loops require declaring an variable as an iterator). Do the tests bomb out if you use Array.prototype.foreach (which is a horrible method that you shouldn't use but it might let you pass this class?)

It feels like the instructor probably wanted to teach a class using haskell or closure or something and they might've been at odds with the department because "no one uses those languages in real life." Which given my entire experience with cs education is completely ironic.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

RPATDO_LAMD posted:

you have some pretty weird standards if you think 100 if-elses is bad but 100 switch cases is suddenly good / "better"
it's all the same poo poo

switch with a lot of cases is easier to understand and debug than if/elseif with a lot of branches - hell i'd say the core of many emulators for cpus is just a giant switch statement - you put all the opcodes in the switch, if there are duplicate instructions you can group them up easily using labels, it's easy to deal with unimplemented opcodes using a default case rather than having to trace through the debugger trying every if statement.... even if the method is huge it's still easy to add opcodes to it if you find new ones etc. meanwhile 100 chained elsifs, the conditions are harder to read, it's harder to add new conditions, there's always the possibility that jimmy put logic in one of the conditions and made it that much harder to understand, and you have to read all the conditions and step through them all all to know if it's going to the "end" at the bottom of the method.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.
Why I am I getting blamed for this third party AI company's gsps not storing in dicom server?

5 minutes later...

Oh no these assholes used group 1337 for their dicom private tag group, this is going to go great.

5 minutes later...

Oh jesus christ not only are a million type 1 tags missing, they're not validating the lengths for any of their VRs etc etc.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

GABA ghoul posted:

:love:

I love this so much, especially because it doesn't even work if you execute it on a German Windows

So here is the correct version that is actually safe to deploy internationally

code:

string decimalSeparator = Directory.Exists("C:\\Programme") ? "," : ".";

is_odd = (number / 2).ToString().Contains(decimalSeparator);

many years ago i used to work as a localization qa tester. did you know the decimal separator is actually a user setting in windows? bugcount go brrr....

quote:

Well, it's plausibly threadsafe, making it less appropriate for this thread. It needs to be rewritten using getting/putenv.
lmao
https://learn.microsoft.com/en-us/dotnet/api/system.threading.thread.currentculture?view=net-8.0

quote:

The CurrentCulture property doesn't work reliably when used with any thread other than the current thread. In .NET Framework, reading the property is reliable, although setting it for a thread other than the current thread is not. On .NET Core, an InvalidOperationException is thrown if a thread attempts to read or write the CurrentCulture property on a different thread. We recommend that you use the CultureInfo.CurrentCulture property to retrieve and set the current culture.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.
Here's a C# version that precomputes all even numbers up to IntMax, which obviously will save on calculation speed. We improve the initialization speed using a Lazy<T> so we only pay the cost of the precomputation on first use of IsEven()

code:
using System;
using System.Collections.Generic;

public static class MemoizedEvenChecker
{
    private static readonly Lazy<HashSet<int>> _evenNumbers = new Lazy<HashSet<int>>(() =>
    {
        var numbers = new HashSet<int>();
        for (int i = 0; i <= int.MaxValue; i += 2)
        {
            numbers.Add(i);
        }
        return numbers;
    });

    public static bool IsEven(int number)
    {
        return _evenNumbers.Value.Contains(number);
    }
}

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.
I thought about it a bit and I think we can use tensorflow for this application. This may or may not work depending upon your CPU type and CUDA version present on your system - when you generate the model, it's important to take a vm of your working environment so you can ensure consistent results.

code:
import tensorflow as tf

model = tf.keras.Sequential([
    tf.keras.layers.Dense(128, activation='relu', input_shape=(1,)),
    tf.keras.layers.Dense(256, activation='relu'),
    tf.keras.layers.Dense(512, activation='relu'),
    tf.keras.layers.Dense(1024, activation='relu'),
    tf.keras.layers.Dense(2048, activation='relu'),
    tf.keras.layers.Dense(1, activation='sigmoid')
])

model.compile(optimizer='adam', loss='binary_crossentropy', metrics=['accuracy'])

X_train = tf.range(0, 1000000, dtype=tf.float32)
y_train = tf.cast(X_train % 2 == 0, tf.float32)

model.fit(X_train, y_train, epochs=10, batch_size=32)

def is_even(number):
    number = tf.cast(number, tf.float32)
    prediction = model.predict([[number]])
    return tf.round(prediction) == 1

print(is_even(2))  # True
print(is_even(3))  # False
print(is_even(42))  # True
print(is_even(777))  # False

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

ultrafilter posted:

It'd be even more efficient to move the precomputation to compile time.

That's actually a great idea! Here's the improved version:

code:
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.Text;
using System.Text;

[Generator]
public class EvenNumberGenerator : ISourceGenerator
{
    public void Initialize(GeneratorInitializationContext context)
    {
    }

    public void Execute(GeneratorExecutionContext context)
    {
        var source = GenerateEvenNumbersCode();
        context.AddSource("EvenNumbers.g.cs", SourceText.From(source, Encoding.UTF8));
    }

    private string GenerateEvenNumbersCode()
    {
        var sb = new StringBuilder();
        sb.AppendLine("using System.Collections.Generic;");
        sb.AppendLine();
        sb.AppendLine("public static class EvenNumbers");
        sb.AppendLine("{");
        sb.AppendLine("    public static readonly HashSet<int> Numbers = new HashSet<int>");
        sb.AppendLine("    {");

        for (int i = 0; i <= int.MaxValue; i += 2)
        {
            sb.AppendLine($"        {i},");
        }

        sb.AppendLine("    };");
        sb.AppendLine("}");

        return sb.ToString();
    }
}

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

ultrafilter posted:

I briefly looked into generating a lookup table using templates but that's way too much effort for me.

I have a French colleague who swears this will work but I have my doubts:

code:
#include <iostream>
#include <array>
#include <climits>

template<int N, int... Ns>
struct EvenNumberGenerator : EvenNumberGenerator<N - 2, N, Ns...> {};

template<int... Ns>
struct EvenNumberGenerator<0, Ns...> {
    static constexpr std::array<int, sizeof...(Ns)> Numbers = {Ns...};
};

template<int N>
struct EvenNumbers {
    static constexpr auto Numbers = EvenNumberGenerator<N>::Numbers;

    static constexpr bool IsEven(int number) {
        return std::binary_search(Numbers.begin(), Numbers.end(), number);
    }
};

int main() {
    constexpr auto evenNumbers = EvenNumbers<INT_MAX>::Numbers;

    std::cout << "Even numbers generated: " << evenNumbers.size() << std::endl;

    // Example usage
    constexpr int number = 42;
    if (EvenNumbers<INT_MAX>::IsEven(number)) {
        std::cout << number << " is an even number!" << std::endl;
    } else {
        std::cout << number << " is not an even number!" << std::endl;
    }

    return 0;
}

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Presto posted:

You guys are missing an obvious optimization. If the number is greater than 2 you first check if it's prime, because every prime number greater than 2 is odd. And since there are infinitely many prime numbers, that greatly reduces size of the problem set.

Slight optimization - only check the set of prime numbers up to the tested number.
code:
function sieveOfEratosthenes(n) {
  const isPrime = new Array(n + 1).fill(true);
  isPrime[0] = false;
  isPrime[1] = false;

  for (let i = 2; i * i <= n; i++) {
    if (isPrime[i]) {
      for (let j = i * i; j <= n; j += i) {
        isPrime[j] = false;
      }
    }
  }

  return isPrime;
}

function isEven(n) {
  const maxNumber = Math.max(n, 2);
  const isPrime = sieveOfEratosthenes(maxNumber);

  if (isPrime[n]) {
    return false; // It's prime, so it can't be even
  }

  const binaryString = n.toString(2);
  const lastBit = binaryString[binaryString.length - 1];

  return lastBit === '0';
}

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Zopotantor posted:

This looks like an ideal use case for blockchain. I'll start the wiki.
I think we can do this. Note that the code for peer to peer and proof of work aspects of blockchain is omitted as an exercise for the reader.

code:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Security.Cryptography;
using System.Text;
using System.Threading.Tasks;

namespace BlockchainIsEven
{
    public class Transaction
    {
        public string FromAddress { get; set; }
        public string ToAddress { get; set; }
        public int Amount { get; set; }
        public byte[] Signature { get; set; }

        public bool Validate()
        {
            // Perform basic transaction validation
            return !string.IsNullOrEmpty(FromAddress) && !string.IsNullOrEmpty(ToAddress) && Amount > 0;
        }
    }

    public class Block
    {
        public int Index { get; set; }
        public DateTime Timestamp { get; set; }
        public string PreviousHash { get; set; }
        public string Hash { get; set; }
        public Transaction[] Transactions { get; set; }

        public void Mine(int difficulty)
        {
            string hashPrefix = new string('0', difficulty);
            while (!Hash.StartsWith(hashPrefix))
            {
                Hash = CalculateHash();
            }
        }

        private string CalculateHash()
        {
            using (SHA256 sha256 = SHA256.Create())
            {
                string rawData = $"{Index}{Timestamp}{PreviousHash}{SerializeTransactions()}";
                byte[] bytes = Encoding.UTF8.GetBytes(rawData);
                byte[] hash = sha256.ComputeHash(bytes);
                return BitConverter.ToString(hash).Replace("-", "");
            }
        }

        private string SerializeTransactions()
        {
            // Serialize transactions to a string representation
            return string.Join(",", Transactions);
        }

        public string CalculateMerkleRoot()
        {
            var transactionHashes = Transactions.Select(t => CalculateHash(t.ToString())).ToArray();
            return BuildMerkleTree(transactionHashes);
        }

        private string BuildMerkleTree(string[] hashes)
        {
            if (hashes.Length == 1)
                return hashes[0];

            var parentHashes = new List<string>();
            for (int i = 0; i < hashes.Length; i += 2)
            {
                if (i + 1 < hashes.Length)
                {
                    var leftHash = hashes[i];
                    var rightHash = hashes[i + 1];
                    var combinedHash = CalculateHash($"{leftHash}{rightHash}");
                    parentHashes.Add(combinedHash);
                }
                else
                {
                    parentHashes.Add(hashes[i]);
                }
            }

            return BuildMerkleTree(parentHashes.ToArray());
        }

        private string CalculateHash(string data)
        {
            using (SHA256 sha256 = SHA256.Create())
            {
                byte[] bytes = Encoding.UTF8.GetBytes(data);
                byte[] hash = sha256.ComputeHash(bytes);
                return BitConverter.ToString(hash).Replace("-", "");
            }
        }
    }

    public class Blockchain
    {
        private readonly List<Block> _chain = new List<Block>();
        private readonly List<Transaction> _pendingTransactions = new List<Transaction>();
        public const int DIFFICULTY = 4;
        public const int BLOCK_REWARD = 10;
        public const int TRANSACTION_FEE = 1;

        public void AddTransaction(Transaction transaction)
        {
            if (transaction.Validate())
                _pendingTransactions.Add(transaction);
        }

        public async Task MineBlock(string minerAddress)
        {
            var block = new Block
            {
                Index = _chain.Count + 1,
                Timestamp = DateTime.Now,
                PreviousHash = _chain.LastOrDefault()?.Hash ?? string.Empty,
                Transactions = _pendingTransactions.ToArray()
            };

            block.Mine(DIFFICULTY);
            _chain.Add(block);
            _pendingTransactions.Clear();

            var coinbaseTransaction = new Transaction
            {
                FromAddress = string.Empty,
                ToAddress = minerAddress,
                Amount = BLOCK_REWARD
            };
            _pendingTransactions.Add(coinbaseTransaction);

            await BroadcastBlock(block);
        }

        private async Task BroadcastBlock(Block block)
        {
            var apiClient = new BlockchainAPIClient();
            await apiClient.BroadcastBlockAsync(block);
        }

        public async Task<bool> IsValidChain()
        {
            for (int i = 1; i < _chain.Count; i++)
            {
                var currentBlock = _chain[i];
                var previousBlock = _chain[i - 1];

                if (currentBlock.Hash != currentBlock.CalculateHash())
                    return false;

                if (currentBlock.PreviousHash != previousBlock.Hash)
                    return false;

                var apiClient = new BlockchainAPIClient();
                if (!await apiClient.VerifyProofOfWorkAsync(currentBlock, DIFFICULTY))
                    return false;
            }

            return true;
        }

        public async Task ResolveConflicts()
        {
            var apiClient = new BlockchainAPIClient();
            var peers = await apiClient.GetPeersAsync();
            var newChain = _chain;

            foreach (var peer in peers)
            {
                var response = await apiClient.GetChainFromPeerAsync(peer);
                var chain = response.Chain;

                if (chain.Count > newChain.Count && await IsValidChain(chain))
                    newChain = chain;
            }

            if (newChain != _chain)
                _chain = newChain;
        }
    }

    public interface IIsEvenStrategy
    {
        Task<bool> IsEvenAsync(int number);
    }

    public class TraditionalIsEvenStrategy : IIsEvenStrategy
    {
        public Task<bool> IsEvenAsync(int number)
        {
            return Task.FromResult(number % 2 == 0);
        }
    }

    public class BlockchainIsEvenStrategy : IIsEvenStrategy
    {
        private readonly Blockchain _blockchain = new Blockchain();

        public async Task<bool> IsEvenAsync(int number)
        {
            var transaction = CreateTransaction(number);
            _blockchain.AddTransaction(transaction);

            await _blockchain.MineBlock("miner1");
            await _blockchain.ResolveConflicts();

            return transaction.Amount % 2 == 0;
        }

        private Transaction CreateTransaction(int number)
        {
            var transaction = new Transaction
            {
                FromAddress = "sender",
                ToAddress = "receiver",
                Amount = number - Blockchain.TRANSACTION_FEE
            };

            // Sign the transaction with a dummy private key
            using (ECDsa ecdsa = ECDsa.Create())
            {
                byte[] transactionBytes = Encoding.UTF8.GetBytes(transaction.ToString());
                transaction.Signature = ecdsa.SignData(transactionBytes, HashAlgorithmName.SHA256);
            }

            return transaction;
        }
    }

    public class IsEvenChecker
    {
        private IIsEvenStrategy _strategy;

        public IsEvenChecker(IIsEvenStrategy strategy)
        {
            _strategy = strategy;
        }

        public async Task<bool> IsEvenAsync(int number)
        {
            return await _strategy.IsEvenAsync(number);
        }
    }

    public class Program
    {
        public static async Task Main(string[] args)
        {
            int number = 42;

            IIsEvenStrategy traditionalStrategy = new TraditionalIsEvenStrategy();
            IsEvenChecker traditionalChecker = new IsEvenChecker(traditionalStrategy);
            bool isEvenTraditional = await traditionalChecker.IsEvenAsync(number);
            Console.WriteLine($"Traditional IsEven: {isEvenTraditional}");

            IIsEvenStrategy blockchainStrategy = new BlockchainIsEvenStrategy();
            IsEvenChecker blockchainChecker = new IsEvenChecker(blockchainStrategy);
            Console.WriteLine("Checking if the number is even using blockchain...");
            bool isEvenBlockchain = await blockchainChecker.IsEvenAsync(number);
            Console.WriteLine($"Blockchain IsEven: {isEvenBlockchain}");
        }
    }
}

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Hammerite posted:

you got chatgpt or something to write all that right? If you sat down and wrote that yourself for the sake of making a joke in the computer programming thread then either you're crazy or i am.

I've been testing the new claude model and it's good at programming humor. It doesn't like violence in source code comments so you still need to use chatgpt for any code that involves violence but it's generally more flexible otherwise.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Foxfire_ posted:

I don't think I hate this that much? it's icky, but it's also plain what it does and how it works.

(I do hate that resume() returns 0 on both the first iteration and after it's finished)

One of the reasons I like the switch statement is how it breaks down into assembly pretty easily...

e.g.
code:
int x = // some value;

switch (x) {
    case 1:
        // Code for case 1
        break;
    case 2:
        // Code for case 2
        break;
    case 3:
        // Code for case 3
        break;
    default:
        // Code for default case
        break;
}
turns into something like
code:
; Assume 'x' is stored in the register eax
    mov eax, [x]      ; Move the value of x into eax
    cmp eax, 1        ; Compare eax with 1
    je case1          ; Jump to case1 if eax is 1
    cmp eax, 2        ; Compare eax with 2
    je case2          ; Jump to case2 if eax is 2
    cmp eax, 3        ; Compare eax with 3
    je case3          ; Jump to case3 if eax is 3
    jmp default_case  ; If none of the above, jump to default case

case1:
    ; Code for case 1
    jmp end_switch

case2:
    ; Code for case 2
    jmp end_switch

case3:
    ; Code for case 3
    jmp end_switch

default_case:
    ; Code for default case

end_switch:
    ; Continuation of code after switch
Pretty logical.

Using that construct in the screenshot is going to result in assembly language that looks like this:
code:
; Pseudo-assembly representation of the 'resume' function in the range_struct

; Assume 'this' pointer is passed in register ecx

resume:
    mov eax, [ecx + state]   ; Load the current state into eax
    cmp eax, At_start
    je  at_start
    cmp eax, In_loop
    je  in_loop
    cmp eax, Done
    je  done

at_start:
    mov dword [ecx + i], 0   ; i = 0
    mov eax, [ecx + stop]    ; Load stop value into eax
    cmp [ecx + i], eax       ; Compare i and stop
    jge done_label           ; If i >= stop, jump to done
    mov [ecx + state], In_loop   ; state = In_loop
    mov eax, [ecx + i]       ; Return i
    ret

in_loop:
    add [ecx + i], [ecx + step]  ; i += step
    mov eax, [ecx + stop]        ; Load stop value into eax
    cmp [ecx + i], eax           ; Compare i and stop
    jge done_label               ; If i >= stop, jump to done
    mov eax, [ecx + i]           ; Return i
    ret

done_label:
    mov [ecx + state], Done   ; state = Done

done:
    xor eax, eax              ; Return 0
    ret
So really gross for no good reason.

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.

Jen heir rick posted:

What about COM. Anyone remember COM? Or DCOM, or COM+. It was supposed to be this magical technology where you could register a COM object and then any program would use it. And when you update with a new version it would automatically work. And you could move those COM objects to a remote server and your program would just magically keep working the same. And any update on the server would be automatically be picked up by the local program.

Except that poo poo didn't work. It was a pain in the rear end. You'd update version and the program keeps picking up the wrong one. And you'd pull your hair out trying to find the right incantation to make it work. Any type of remote COM had to be carefully designed to be called remote. So that's a leaky abstraction. poo poo was worse than what we had, which was just shared libraries resolve by PATH. Which is what we have now, which shows you how lovely com was.

Of course I haven't worked with COM in like 20 years So I may not remember the specifics, but I do remember COM sucking poo poo, and having to pierce the vale of magic was often needed to get poo poo to work correctly.

My favorite part of COM was working with BSTR. It's a special string type that was used for com interfaces, as many different programming languages could interop with COM so you couldn't use, say, a std::string.

This doesn't sound so bad, but in the early days of windows, ms did performance profiling and found out that string allocations involving BSTR were slow - so MS built a BSTR cache into Windows - e.g. https://devblogs.microsoft.com/oldnewthing/20150107-00/?p=43203.

One of the issues with this cache is that it covers up issues involving string allocation across COM boundaries. For instance, say you have the audacity to return a bstr_t (which is a smart pointer to a bstr) from a COM interface. What will happen is that your program will work fine for about ten minutes, and then randomly crash with a heap corruption issue - this is because the BSTR cache will cover up that the bstr_t deallocated the string when it went out of scope, but once the BSTR is evicted from the cache you are hosed.

In order to catch an issue like this, you can set OANOCACHE=1 - this turns off the BSTR cache in the oleaut32.dll, so your program will crash immediately if you return a bstr_t instead of after ten minutes. This is also why you need to set OANOCACHE=1 when using mallocspy, as otherwise it may report bstr leaks erroneously.

Adbot
ADBOT LOVES YOU

Bruegels Fuckbooks
Sep 14, 2004

Now, listen - I know the two of you are very different from each other in a lot of ways, but you have to understand that as far as Grandpa's concerned, you're both pieces of shit! Yeah. I can prove it mathematically.
its almost impossible to avoid getting sued for something if you work as a software developer long enough and release enough products - you can do all the patent search and perform all the rituals you want to try to ensure that you don't get sued and still end up with a lawsuit because someone has the software patent on an arrow that faces to the right indicating that a submenu is present on a context menu and your patent search should've picked up on that fact.

  • 1
  • 2
  • 3
  • 4
  • 5
  • Post
  • Reply