36 karma · joined June 15, 2016
1. a way to record logical changes to files (e.g. implement two features without making any commits, then when you're done, pick out the files/chunks that encode each feature and create commits out of them),
2. a record of history (e.g. just start writing code and make a commit every time you compile/run tests without unexpected failures),
3. something else?
I've found it very painful to apply my git-adapted workflow to Perforce: I _want_ to just start coding, testing out various possible design choices and implementations instead of only theorizing about them, but can't (e.g. "I wonder if I could factor out these methods + fields into a different class?" Perforce: oh well, I guess I should write it down somewhere to remember for later. Git: branch my current work, spend five minutes sketching an extraction, then realize it's insane and continue working). Am I crazy and just don't realize ow much better the Perforce model is?
Related:
[1]: https://dubroy.com/blog/method-length-are-short-methods-actu...
[1]: http://lambda.jstolarek.com/2012/03/function-composition-and...
So I agree that enormous blobs of unreadable crap are indeed unreadable, and that regardless of how neat and functional your code is, it can still be complete gibberish to most people. That being said, long chains of streams can be broken out quite nicely by using intermediate names:
e.g.
Comparator<Transaction> descendingTransactionsByValue = comparing(Transaction::getValue).reversed();
Stream<Transaction> groceries = transactions.filter(t -> t.getType() == Transaction.GROCERY);
Stream<Transaction> sortedGroceries = groceries.sorted(descendingTransactionsByValue);
Stream<Transaction> transactionids = sortedGroceries.map(Transaction::getId).collect(toList());
vs. the first code block under "Figure 1" in the linked article.For me at least, it helps keep code from getting too unruly: you only have one 'thing' you can do in a filter, map or sorted call, unlike in a foreach loop where anything can go. So my thesis is this: using streams I can quickly scan over the function/stream names to get the gist of what it's doing, but using foreach loops I need to closely examine each line to have any idea of what's happening :3 (e.g. people love abusing labeled breaks [1] in our codebase, as well as excessively modifying input parameters w/o documentation, so I might be a bit biased against for loops)
[1]: https://stackoverflow.com/questions/14960419/is-using-a-labe...
I guess what I'm getting at is rushing to the conclusion that xenophobia is the only deciding factor here seems a bit premature, and that the problem itself is likely multifaceted.
[1]: https://en.wikipedia.org/wiki/Food_safety_incidents_in_China
Re. countries vs corporations: countries in isolation make laws for themselves (consumer protection, long-term economic protection, etc.), whereas corporations must abide by the laws of their host countries (hence tax evasion via incorporation in accommodating countries). If two countries start to compete, there isn't really anything that stops them from annihilating one another in disturbing fashions (e.g. erecting walls, slinging propaganda, blockading, etc.) other than treaties. Get enough treaties together and you get the EU.
Unlike Frege where I (might? Frege's the only language of the three that I haven't investigated thoroughly) can point learners to essentially any Haskell tutorial and have them vaguely do 'the right thing', there exists a subset of Scala developers who use the language like Java with type inference. With Frege I could, for example, merely enforce the minimal usage of IO or State, but doing so with Scala is more complicated (maybe force the usage of cats/scalaz and their equivalent monads? It's still very easy to not use them, however). If there were an equivalent to F# on the JVM I'd settle on it in a heartbeat, but the dearth of well supported, pure functional languages makes this a tough choice. All in all, I'll probably go with pure4j, but it would be nice to stop writing Java at some point in my career.
That's all just my opinion, of course, and I hardly have enough industry experience to back up its validity! 'Just sanity checking my reasoning :)
[1]: https://github.com/Frege/frege/graphs/contributors
[2]: https://github.com/xclerc/ocamljava/graphs/contributors
You're right, though; pure4j offers an immediate and easily obtainable win, so it'd definitely be an easier pill to swallow. Thanks :)
Question: what do you think of the thesis of pure4j [1] vis. frege [2]? Namely, are the advantages gained by switching to a haskell-like language far above those attained by simply forcing effects into a small part of the codebase?