Sunday, April 07, 2024

Useful FFmpeg Commands

FFmpeg is a great command-line tool for dealing with audio and video files. Here are a couple of useful commands:

Extract audio from a video
$ ffmpeg -i video.mp4 -q:a 0 -map a audio.mp3
Concatenate multiple videos into a single file

First, create a file containing the list of videos to concatenate, and then pass it through ffmpeg:

$ cat list.txt
file '/path/to/file1.mp4'
file '/path/to/file2.mp4'
file '/path/to/file3.mp4'

$ ffmpeg -safe 0 -f concat -i list.txt -c copy output.mp4

Related post:
FFmpeg Cheatsheet

Monday, January 01, 2024

fahd.blog in 2023

Happy 2024, everyone!

I'd like to wish everyone a great start to an even greater new year!

In keeping with tradition, here's one last look back at fahd.blog in 2023.

During 2023, I posted 11 new entries on fahd.blog. I am also thrilled that I have more readers from all over the world! Thanks for reading and especially for giving feedback.

Top 3 posts of 2023:

I'm going to be writing a lot more this year, so stay tuned for more great techie tips, tricks and hacks! :)

Related posts:

Saturday, December 09, 2023

Python: Running Tasks in Parallel

The concurrent.futures module can be used to run tasks in parallel in Python. Here is an example:

import concurrent.futures
from concurrent.futures import ProcessPoolExecutor

with ProcessPoolExecutor(max_workers = 10) as executor:
    futures = [executor.submit(perform_task, task) for task in tasks]
	
results = [future.result() for future in futures]

The ProcessPoolExecutor class uses a pool of processes to execute tasks asynchronously. The submit function immediately returns a Future object, and you can call future.result(), which will block until the task has completed.

Note that there is also a ThreadPoolExecutor class which uses a pool of threads; however, due to the Global Interpreter Lock, only one thread can execute python bytecode at any one time, which means that you will not achieve any parallelisation in most cases.

Sunday, December 03, 2023

Java 21: Sequenced Collections

Introduced in Java 21, a SequencedCollection is a Collection whose elements have a defined encounter order i.e. it has first and last elements, and the elements between them have successors and predecessors. Some examples include List, Deque, SortedSet, and LinkedHashSet.

The SequencedCollection interface provides methods to add, retrieve, and remove elements at either end of the collection. It also has a reversed() method which provides a reverse-ordered view of the original collection.

Similarly, the new SequencedMap interface is a map that has a well-defined encounter order, supports operations at both ends, and is reversible. Examples include LinkedHashMap and TreeMap.

Example usage:

var set = new LinkedHashSet<String>(Arrays.asList("a", "b", "c"));

set instanceof SequencedCollection
==> true

set.getFirst()
==> "a"

set.getLast()
==> "c"

set.reversed()
==> [c, b, a]

Saturday, December 02, 2023

Java 21: Unnamed Classes

Java 21 introduces Unnamed Classes (a preview language feature) that allow you to write small programs without having an enclosing class declaration.

Here is the classic Hello World program that we were all taught when starting to learn Java:

public class HelloWorld { 
  public static void main(String[] args) { 
    System.out.println("Hello, World!");
  }
}

There is a lot of clutter here. Using an unnamed class, this can be simplified to:

void main() { 
  System.out.println("Hello, World!");
}

Not only is the enclosing class not required, but the main method has also been enhanced so that it does not need to be public, static or require any arguments.

You can also add fields and methods to an unnamed class, as shown below:

private static final String GREETING = "Hello, World!";

private String getGreeting() {
  return GREETING;
}

void main() { 
  System.out.println(getGreeting());
}

Since an unnamed class cannot be instantiated or referenced by name, it is only useful as a standalone program or as an entry point to a program.