Migrated to Hugo
I decided to migrate my old blog from Jekyll to Hugo framework.
I decided to migrate my old blog from Jekyll to Hugo framework.
This command searches all .log files which contains the target message in the current directory. It prints the filename, the matching line and the 30 lines that follow the matching line. grep -H -A 30 "target error message" *.log This command locates every line that contains the target message (-i here is for ignoring case distinctions) and prints it, along with the 30 lines that immediately follow each matching line. | less provides paging functions. grep -i -A 30 "target error message" sample.log | less tail -f starts continuously outputting new lines as they are written to the specified file. grep then, in real-time, scans these incoming lines and print necessary logs. This process continues indefinitely until we manually stop the command. tail -f sample.log | grep -A 30 "target error message" This command counts the occurrences of the target error message in the sample.log. grep -c "target error message" sample.log This command prints 30 lines of context both before and after the target message in the sample.log. grep -C 30 "target error message" sample.log Nowadays we have more useful tools such as ELK (Elasticsearch, Logstash, Kibana) stack. The configuration is more complicated so I guess I will add those contents in the future :)
DP code sample. Just a quick refresh. class Program { static void Main() { int goal = 97; int[] coins = {10, 25, 5, 1}; int []table = new int[goal + 1]; table[0] = 0; for (int i = 1; i <= goal; i++) { table[i] = int.MaxValue; } for (int j = 1; j <= goal; j++) { for (int k = 0; k < coins.Length; k++) { int selectedCoin = coins[k]; if (selectedCoin <= j) { table[j] = int.Min(table[j], table[j - selectedCoin] + 1); } } } foreach (var elem in table) { Console.Write(elem); Console.Write(" "); } Console.WriteLine(); Console.WriteLine(table.Last()); } }
Steps may change in the future. sudo snap remove firefox Follow https://support.mozilla.org/en-US/kb/install-firefox-linux#w_install-firefox-deb-package-for-debian-based-distributions However, in step 5: onfigure APT to prioritize packages from the Mozilla repository, use the command below: echo ' Package: * Pin: origin packages.mozilla.org Pin-Priority: 1001 Package: firefox Pin: version 1:1snap* Pin-Priority: -1 ' | sudo tee /etc/apt/preferences.d/mozilla-firefox sudo apt install firefox To ensure that unattended upgrades do not reinstall the snap version of Firefox: echo 'Unattended-Upgrade::Allowed-Origins:: "namespaces/moz-fx-productdelivery-pr-38b5/repositories/mozilla:mozilla";' | sudo tee /etc/apt/apt.conf.d/51unattended-upgrades-firefox
Minimal API is a fairly new way to implement Web APIs, introduced in .NET 6. I initially thought it was only suitable for small projects, as its name suggests. Recently, I read some articles and watched videos about how to organize Minimal API projects, and I have changed my mind. The main reason I believed Minimal API was only for small projects is that most demos are quite small and put all APIs in Program.cs, which is obviously not scalable and somewhat messy. By using extension methods, it is quite convenient to group APIs into different files, making them much easier to manage. A third-party library Carter also seems useful in grouping APIs. ...
Use escape sequences for special signs such as \n. Or use a verbatim statement // Escape sequences example Console.WriteLine("I need to use escape sequences for special signs such as \\ here."); // Verbatim statement example Console.WriteLine( @" My name is ""SilMOON"" and this is a verbatim statement. I can use special signs such as \ here. " ); Noted that C#11 introduced raw string literals which is more convenient. I’m actually suprised that they didn’t add this feature earlier. :) ...
Add non-root user. I. # useradd -m USERNAME II. # passwd USERNAME III. Add your user to the wheel or sudo group: DEB based distros: # usermod -aG sudo USERNAME RPM based distros: # usermod -aG wheel USERNAME Disable root logins. I. # vim /etc/ssh/sshd_config II. Set PermitRootLogin=no Change SSH port Use non-root user (Just my preference) Install zsh & oh-my-zsh Set up SSH keys If no exsisting key, generate one first On local machine: $ ssh-copy-id USERNAME@IP_ADDRESS (If SSH port changed: $ ssh-copy-id -p PORT USERNAME@IP_ADDRESS) Configure ufw firewall ...
Use vararg for variable arguments: fun printLetters(vararg letters: String, count: Int): Unit { print("$count letters are ") for (letter in letters) print(letter) println() } Then we can use it by calling: printLetters("a", "c", "q", count = 3) Or use * to pass an array as parameters: val argArray = arrayOf("q","e","w") printLetters(*argArray, count = 3) An example of fold function: fun cal(list: List<Int>): Int { return list.fold(0){ res, el -> res * el + el } } If we call: ...
We can use the netstat -anp command to check active connections and port usage. -a shows all active connections. -n shows applications an port number in numbers. -p lists processes(pid) which occupied the port. And we can simply kill them using the pid if we need.
The this keyword has two meanings: to refer a field of the implicit parameter and to call another defined constructor in the same class. The super keyword also has two meanings: to call a superclass constructor and call a superclass method. Like using this keyword to call a constructor, the constructor call must be the first statement in the new constructor. In the following example, Manager is the subclass of Employee, the Employee class which is hidden for simplicity does not have the field bonus: public Manager(String name, double salary, int year, int month, int day) { super(name, salary, year, month, day); //is the same as Employee(name, salary, year, month, day) bonus = 0; } Likewise, the this keyword can be used in a similar way. ...