[ overboard / sfw / alt / cytube] [ leftypol / b / WRK / hobby / tech / edu / ga / ent / 777 / posad / i / a / R9K / dead ] [ meta ]

/edu/ - Education

Learn, learn, and learn!
Name
Email
Subject
Comment
Flag
File
Embed
Password (For file deletion.)

Matrix   IRC Chat   Mumble   Telegram   Discord


File: 1622811198330.jpg ( 72.84 KB , 1000x667 , rubbo ducko.jpg )

 No.5982

Hello edu, I am a curious yet ADD retard that finds it difficult to grasp anything through reading and I offer you my services;
See some people find it helpful to improve their understanding of a topic by explaining it to someone else. If you are one of these people please feel free to try and explain what it is you are working on and I will try my best to grasp what you are saying though active listening.Win win
>>

 No.5983

Based
>>

 No.5985

I usually imagine lecturing people about interesting topics while taking a walk. Actually writing things down is too much work. Is there anything you are interested in?
>>

 No.6100

>>5982
I am working currently on getting them bitches, respectfully
>>

 No.6551

File: 1627122585821.jpg ( 70.98 KB , 900x900 , curious pepe.jpg )

>>5985
That's cool anon. Yeah I especially want to know about history, economics or psychology among other subjects. I am really poor at math but I'm trying to improve if anon wants to take a crack at it? I'd love to learn about any topics you guys want to talk about
>>

 No.6552

>>5982
Free monads are very scary but they are actually more simple than you'd think if you ignore all the irrelevant stuff.

First step is to create an instruction set or an API, or whatever you want to call it.
I'll be using a pseudo-code fake OOP language to make it easier to understand.

class API; // the parent class

class AddUser(u: User) extends API
class GetUser(username: String) extends API

etc.

Think of it like an enum (or an ADT), but with stuff. Here's another alternative implementation in another different but also fake language:

type API =
AddUser(u: User) |
GetUser(username: String)


The purpose of this is to use it in your program.
In an imperative language, it would look like this:
class API; // the parent class

class AddUser(u: User, next: API) extends API
class GetUser(username: String, next: API) extends API
class End extends API

function API logIn(username: String, password: String){
new GetUser(username, new ComparePasswords(password, new RegisterLogin(user, new SignCookie(cookie, new End))));
}

Ok that's cool but what the fuck is this anyways?
It's a data structure that tell you instructions. As you can see, it uses variables that aren't even available, namely, "user" and "cookie". It's not even a complete implementation.

In more functional programming languages we can do something like this instead (now shamelessly using scala-like language):


def logIn(username: String, password: String) return API[Cookie]{
for {
user <- GetUser(username)
isValidPassword <- ComparePasswords(password)
cookie <- RegisterLogin(user)
signedCookie <- SignCookie(cookie)
} return signedCookie

The interesting part here is that this is still just a nested data structure, even if it doesn't look like one. Reducing the complexity a bit, the data structure is around the same as the above, namely:
new GetUser(username, new ComparePasswords(password, new RegisterLogin(user, new SignCookie(cookie, new End))))

This is useful because you can then iterate through this data structure and replace GetUser for a real get user call.

def interpret(api: API){
switch(api):{
case GetUser(username):
return databaseCall(username)
….
}
}

This means that your program can be purely descriptive, with no concrete implementation, and then supply the implementation somewhere else. It also means you can swap out implementations at any time without changing the description of your program.
eg.
switch(api):{
case GetUser(username):
verifyUsernameIsValid(username) // this was added, without changing the logIn function
return databaseCall(username)
….
}

And these compose, so you can do something like:

def signIn(username, password): API[Boolean]:
for {
user <- logIn(username, password)
isSuccess <- sendEmailNotification(user.email)
} return isSuccess

Then, where you want to use this, you need to supply the interpreter.

def signInRequestHandler(username, password){
val programDescription: API[Boolean] = signIn(username, password)
intepreter(programDescription) // runs the function with the switch statement
}


Everything else related to this is just the machinery to make this possible.
The Free monad gives your API the "nested" structure.
Inject/liftF, etc just make it easy to work with this shit.
FunctionK, ~>, natural transformation: It's the function called interpreter. Fancy names for a mundane purpose.

So yeah, at the end you'll get somewhat incomprehensible code that makes all of this come together.


Bonus:
If you have several APIs, say Api1, Api2, and Api3, you need to supply extra machinery to compose these.
Namely the Inject stuff, and EitherK/Coproduct stuff. You seriously don't need to understand how this works.

Api1and2 = EitherK[Api1, Api2, a]
Api1and2and3 = EitherK[Api3, Api1and2, a]

Then when you use this shit, you need to supplant more "switch functions" ie "interpreters".

def signInRequestHandler(username, password){
val programDescription: Api1and2and3[Boolean] = signIn(username, password)
val interpreter1or2or3: Function = (interpreter1 or interpreter2 or interpreter3) // or is a magic operator that joins these functions
interpreter1or2or3(programDescription)
}

All you need to do to use this is to understand how to define the machinery. But these are the basic concepts without any type level bullshit.
>>

 No.6553

>>6552
>>5982
Also sorry OP. This is "advanced" computer science/ software engineering stuff. I also skipped a lot of pre-requisite concepts, so unless you're already balls deep into this stuff, it will be hard to understand.

feel free to ignore.
>>

 No.6554

>>6552
Isn't this just the interpreter pattern for functional programming nerds?
>>

 No.6555

>>6552
>>6553
That's cool anon, why exactly are we calling a user?
>>

 No.6556

>>6554
yeah, I hadn't noticed that.
https://www.youtube.com/watch?v=hmX2s3pe_qk
this is a good talk on the subject.

"the interpreter pattern is the only useful patter in the GoF book" lmao.
>>

 No.6557

>>6556
> "the interpreter pattern is the only useful patter in the GoF book" lmao.
That's a bit unfair, the visitor pattern is pretty cool and so are the strategy and state patterns.
>>

 No.6558

>>6557
I dislike OOP tbh. I don't use it that much, nor do I do fancy enough shit to merit it.

This Free stuff is nice if your language has a nice type system.
>>

 No.6561

>>6558
Give Smalltalk a try, it will change your views on OOP for sure: https://mooc.pharo.org/
>>

 No.6571

>>6555
This would be part of a larger program.
>>6561
Hmmm I'll look into it. I've never heard anyone use smalltalk for modern shit.

Unique IPs: 9

[Return][Catalog][Top][Home][Post a Reply]
Delete Post [ ]
[ overboard / sfw / alt / cytube] [ leftypol / b / WRK / hobby / tech / edu / ga / ent / 777 / posad / i / a / R9K / dead ] [ meta ]
ReturnCatalogTopBottomHome