2023-02-10
.
Web Serial API provides a way for websites to receive data from and send data to serial devices. The target can be a device connected via a serial port, or a USB or Bluetooth device acting as a serial port. MDN
return one's gaze
GUI development and moves to avoid destructive updates
There is a movement around Java to avoid "inheritance for the purpose of implementation reuse. For example, the Abstract Window Toolkit (AWT) released in 1995 had a rule of "inheritance and overriding various methods. However, the Standard Widget Toolkit (SWT) used by Eclipse and others now has a "do not inherit" rule.
What developed instead was the concept of "delegation."
Hooks API and Function Components
Reactive Programming System Flow
// Specify the data source.
int[] scores = { 97, 92, 81, 60 };
// Define the query expression.
IEnumerable<int> scoreQuery =
from score in scores
where score > 80
select score;
// Execute the query.
foreach (int i in scoreQuery)
{
Console.Write(i + " ");
}
// Output: 97 92 81
- [Language-Integrated Query (LINQ) (C#) | Microsoft Learn](https://learn.microsoft.com/en-us/dotnet/csharp/programming-guide/concepts/linq/)
- Write SQL-like query language for arrays and other collections
int sum = widgets.stream()
.filter(w -> w.getColor() == RED)
.mapToInt(w -> w.getWeight())
.sum();
- [Stream (Java Platform SE 8)](https://docs.oracle.com/javase/jp/8/docs/api/java/util/stream/Stream.html)
- Of course, each method call does not create a large temporary object
public record Person(string FirstName, string LastName);
- [record-class](https://docs.oracle.com/javase/jp/15/language/records.html)
java
record Rectangle(double length, double width) { }
- > The record class declares a set of fields, and the appropriate accessors, constructors, equals, hashCode and toString methods are automatically created. The fields are FINAL because this class is intended to function as a simple "data carrier".
- > This concise declaration is equivalent to the following standard classes
java
public final class Rectangle {
private final double length;
private final double width;
public Rectangle(double length, double width) {
this.length = length;
this.width = width;
}
double length() { return this.length; }
double width() { return this.width; }
// Implementation of equals() and hashCode(), which specify
// that two record objects are equal if they
// are of the same type and contain equal field values.
public boolean equals...
public int hashCode...
// An implementation of toString() that returns a string
// representation of all the record class's fields,
// including their names.
public String toString() {...}
}
- Q: Very simple struct?
- A: The major difference between STRUCT and STRUCT is that destructive renewal is prohibited.
- Q: Can't I just assign first? object that simply transfers data?
- A: Yes. Until now, the means to create such objects could not be realized without writing a lot of code.
- In the course of development in 2009 or so, Java and C# changed because "it's not right that the object conveyed here is destructible" and "we need a way to easily apply an indestructible object".
- Q2: Do you mean const data?
- A2: I would say so.
Q3: I think only mutexes will have the desire to have variable
The same way the function component returned a virtual DOM in React that I mentioned earlier.
Brief summary
Promise and async/await
An open standard for sound, interoperable JavaScript promises—by implementers, for implementers.
promise2 = promise1.then(onFulfilled, onRejected);
// callback style
do_something(params, on_success, on_error);
js
r = new Request(params);
r.on_success = on_success;
r.on_error = on_error;
r.send()
- In the past, JavaScript used `XMLHttpRequest` to hit APIs of other services, which was a style of using event handlers
- [Using XMLHttpRequest - Web APIs | MDN](https://developer.mozilla.org/en-US/docs/Web/API/XMLHttpRequest/Using_XMLHttpRequest)
- This was troublesome, so third-party libraries tried, and the style of using Promise became the de facto standard.
- After that, a Promise-using style API was standardized.
- [Fetch API - Web APIs | MDN](https://developer.mozilla.org/en-US/docs/Web/API/Fetch_API)
- What was the trouble? Many things:.
- Writing what you want to do after asynchronous processing first in the source code is confusing the flow of thought.
- Error handling when asynchronous process 1 is performed, followed by asynchronous process 2 using the result of asynchronous process 1, and so on.
- It is defined this way at [Promises/A+](https://promisesaplus.com/) so it can be written in one place
- > If `onRejected` is not a function and `promise1` is rejected, `promise2` must be rejected with the same reason as `promise1`.
- In the style of callbacks and event handlers, you would make it a named function and specify it in `on_error` here and there
def foo(x: int):
y: str = x # NG
- `error: Incompatible types in assignment (expression has type "int", variable has type "str") [assignment]`
java.lang.Object type?def foo(x: int):
y: object = x # OK
python
def foo(x: object):
y: str = x # NG
- `error: Incompatible types in assignment (expression has type "object", variable has type "str") [assignment]`
- Attempting to assign a value of type Object to a value of type String (implicit downcasting) is not allowed.
- This is normal type behavior.
- That ANY is a special type that can implicitly perform both upcasting and downcasting.
- 
- In TypeScript, the types corresponding to these two behaviors are unknown and any
ts
const take_number = (x: number): void => {};
{
let x: any;
take_number(x); // OK
}
{
let x: unknown;
take_number(x); // NG
}
- `Argument of type 'unknown' is not assignable to parameter of type 'number'.`
def foo(x: int):
return x
print(typing.reveal_type(foo))
- `note: Revealed type is "def (x: builtins.int) -> Any"`
- This is a different behavior from TypeScript
- 
- It is expected that humans will explicitly state this
python
def foo(x: int) -> int:
return x
print(typing.reveal_type(foo))
- `note: Revealed type is "def (x: builtins.int) -> builtins.int"`
Nomenclatural and structural typing
from Draft addition to "The Difference Between Named Type Systems and Structural Type Systems"
int n; or something like that.There are two approaches to this "meta-information on variables"
C++, born in 1985, and Java, born in 1995, used a nominal type system.
extends and implements.On the other hand, structural type systems were more dominant in type theory research.
Example in TypeScript TypeScript
type T1 = {
x : number
}
type T2 = {
x : number
}
let a: T1;
let b: T2 = {x: 1};
a = b; // OK
- The `{x: 1}` part of `let b:T2 = {x: 1}` in this code is an unnamed object type.
- This has the same form as both T1 and T2, so it can be substituted without error.
Rust: Ownership/Lifetime
let x = String::from("hello");
let y = x;
println!("x: {}", x); // NG
println!("y: {}", y);
- `error: borrow of moved value: x`
- x and y are unique_ptr in C++, and the move is done with `y = x`.
- C++ usually tries to copy references.
- Use `std::move` to express "we intend to move, not copy".
- The "right side value/left side value" distinction was added in C++11 to achieve this without breaking existing code
- If a value is a right-hand side value, then it is not used in the future and should be moved, not copied.
- Thus, a move constructor that accepts right-hand side value references is added
- std::move casts to a right-hand side value reference so that the move is performed
#include <iostream>
#include <string>
#include <memory>
int main () {
std::unique_ptr<std::string> x = std::make_unique<std::string>(std::string("abc"));
std::unique_ptr<std::string> y;
y = std::move(x);
std::cout << *y << std::endl;
std::cout << *x << std::endl; // here
}
output
abc
Segmentation fault
- In this code, x is null so that it cannot be read or released by mistake
let x = String::from("hello");
foo(x); // move
println!("x: {}", x); // NG
- In this example, x moves at the function call, so it can't be used after that.
- The compiler will follow the move by assignment or function call and release at "the point where it exits the scope without moving".
Concept of Lifetime
let x;
let y;
// println!("x: {}", x); // NG
// error[E0381]: used binding `x` is possibly-uninitialized
x = String::from("hello");
println!("x: {}", x); // OK
y = x;
// println!("x: {}", x); // NG
// error[E0382]: borrow of moved value: `x`
- The use of x before initialization and after move is shown to be a compile error
'a, the same as naming a type variable T in generics.rust
fn longest(x: &str, y: &str) -> &str { // NG
if x.len() > y.len() {
x
} else {
y
}
}
error
error[E0106]: missing lifetime specifier
--> src/main.rs:14:33
|
14 | fn longest(x: &str, y: &str) -> &str {
| ---- ---- ^ expected named lifetime parameter
|
= help: this function's return type contains a borrowed value, but the signature does not say whether it is borrowed from `x` or `y`
help: consider introducing a named lifetime parameter
|
14 | fn longest<'a>(x: &'a str, y: &'a str) -> &'a str {
| ++++ ++ ++ ++
- Example 2
- static lifetime
- Lifetime specifiers named in advance by the system
- It represents "lifetime across the entire program."
rust
fn dangle() -> &String {
let s = String::from("hello");
&s
}
error
error[E0106]: missing lifetime specifier
--> src/main.rs:22:16
|
22 | fn dangle() -> &String {
| ^ expected named lifetime parameter
|
= help: this function's return type contains a borrowed value, but there is no value for it to be borrowed from
help: consider using the `'static` lifetime
|
22 | fn dangle() -> &'static String {
| +++++++
- This is inherently no good.
- Because s is released when exiting the function.
- But the compiler decides, "Well, if I change it to a constant, I can make the whole program lifetime.
- The result is an error message that's two steps ahead of the rest of us.
- If you make it so that the compiler doesn't know if it can be made into a constant, you'll get a straightforward error message.
rust
fn dangle(x: &String) -> &String {
let s = x.clone();
&s
}
error
error[E0515]: cannot return reference to local variable `s`
--> src/main.rs:31:5
|
31 | &s
| ^^ returns a reference to data owned by the current function
This page is auto-translated from /nishio/プログラミングの変化勉強会 using DeepL. If you looks something interesting but the auto-translated English is not good enough to understand it, feel free to let me know at @nishio_en. I'm very happy to spread my thought to non-Japanese readers.