Jekyll2025-08-21T03:22:16-07:00https://pegah-kh.github.io/feed.xmlPegah Khayatanpersonal descriptionPegah KhayatanFuture Blog Post2199-01-01T00:00:00-08:002199-01-01T00:00:00-08:00https://pegah-kh.github.io/posts/2012/08/future-postThis post will show up by default. To disable scheduling of future posts, edit config.yml and set future: false.

]]>
Pegah Khayatan
CF-969-D12024-09-15T00:00:00-07:002024-09-15T00:00:00-07:00https://pegah-kh.github.io/competitive-programming/blog-post-4C

The question

Summary of the question: The goal is to count the number of brilliant consecutive subarrays of a given array. What is a brilliant array? an array (that now is no more important if set or array) from which we can arrive at a set of consecutive numbers by taking the mean of two elements in the set (the procedure may obviously be repeated several times). The length of the given array does not exceed 4x1e5.

Initial thoughts:

  1. just counting the number of these subsets is important, not determining them.
  2. It is interesting thing to notice that a produced number is always the average of 2, 4, 8, … numbers in the set (if we use the same number n times, we count it n times! for example, if we have a,b,c in the set and then (a+b)/2=d and then (d+c)/2=e, then e is actually (a+b+c+c)/4)
  3. we know what are the lowest and highest numbers in the set, and producing numbers between min and max and like producing numbers, only shifted, between 0 and max-min. Shifting does not change the brilliance of a set!

Post-initial thoughts:

  • still thinking :D

B

The question Solved; revision on the algorithm to add …

]]>
Pegah Khayatan
Articulation Points2024-09-15T00:00:00-07:002024-09-15T00:00:00-07:00https://pegah-kh.github.io/competitive-programming/articulation-pointArticulation Points & Bridges in an Undirected Graph

[Disclaimer: All (or almost all) that is explained here is from the Steven and Felix Halim and Suhendry Effendy book.]

Articulation point in a graph: if you take out this node, your graph will split up in two parts ….. Bridge: the same thing would happen if you take such an edge out …..

The goal is to find such nodes or edges in an undirected graph. I have never really used this algorithm in any problem I have solved, as far as I remember :U … but it’s a fun one, like it has those moments where you go : Aaaaaaaaaaaa, that’s why :U (this thing: :U is such a mood)(I should just quit writing otherwise I will just continue jabbering and babbering about nonesense, so, let’s stop it here)

What would be the stupid way to find such vertices or edges? Just take out each node or edge one by one and check if the graph remains connected. The complexity would be O(Vx(V+E)), one is for taking out each node/edge, and the other for an algorithm to run through the graph, BFS or DFS, and check if we can access all nodes starting from one.

But let’s be wiser, and make some changes to DFS to make it serve our goal better; define two numbers to store for each node when applying DFS:

  1. dfs_num : The iteration at which we visit a node
  2. dfs_low : If R is the set of nodes in the DFS spanning subtree rooted at u, then dfs_low is the lowest dfs_num that can be found in R OR among the ones not in R but reachable by a back edge from R.

alt text

Let’s say we have done DFS over the graph and now we have all the numbers we wanted to store. consider a vertex u connnected to v, and add the condition dfs_low(v) $\geq$ dfs_num(u). What does this mean?

alt text

This means that we have not been able to find a lower dfs_num in the DFS subtree rooted at v or among those connected to it by a back edge. In other words, the nodes visited during DFS after visiting the node v all have higher or equal dfs_nums than that of v, which also means that there is no back edge from nodes visited in DFS after v back to the nodes visited before that point, and hence u is an articulation point! Exceptional Case: when the starting node of DFS has only one neighbor, it is obviously an articulation point; but, we cannot detectc it using the above process since it has the lowest dfs_num of all.

Detecting Bridges is similar, but the condition to check on vertices changes just a bit: dfs_low(v) $>$ dfs_num(u) . There is no equal as you can observe :U

Why?

]]>
Pegah Khayatan
Fenwick Tree2024-09-15T00:00:00-07:002024-09-15T00:00:00-07:00https://pegah-kh.github.io/competitive-programming/binary-numsFenwick Tree (Binary Indexed Tree)

A Fenwick Tree (also Binary Indexed Tree (BIT)) is a useful data structure to calculate sum of a consecutive subset (also known as Range Sum Query (RSQ)) in an ordered set.

The advantage is that we can use it to update elements efficiently, in O(log n).

Another cool thing: we can use bit manipulation techniques for more efficiency.

Each node is responsible for the sum of elements in a coonsecutive subset; which one? the node $i$ keeps the sum for the subset $[(i - LSOne(i)+1), …, i]$. ($LSOne(i)$ for a binary number gives the least significant bit that is one. For example, for $6$ it would be $2$.)

Why is it structured like this? becuase then we can easily and efficiently:

  1. compute $rsq(i,j)$
  2. update the value of an item at index $i$ (and the tree accordingly)

First, if we want to compute $rsq(i,j)$, we can just calculate $rsq(1,j)$ and $rsq(1, i-1)$ and the substract them from eachother; so it boils down to computing $rsq(1,i)$.

if $i^{\prime} = i - LSOne(i)$ (what is does is simply removing the least significant one-bit and keeping the rest) did you what happened there? :D we had the node $i$ responsible for the subset $[(i - LSOne(i)+1), …, i]$, and then the node $i^{\prime}$ is responsible for $[(i^{\prime} - LSOne(i^{\prime})+1), …, (i - LSOne(i))]$, and … ; so, if we continue like that, till reaching zero, we get the sum of all elements from $1$ to $i$. \(rsq(1,i) = n_{i} + n_{i^{\prime}} + n_{i^{\prime \prime}} ...\)

The complexity? $O(log n)$.

Secondly, we want to update the element at the index $i$, Let’s say we want to add $v$ to it : what nodes would this update affect? all the nodes such as $j$ where $ i \in [(j - LSOne(j)+1), …, j]$; what are those? those that when you drop their least significant one-bit are less than $i$ but are larger than $i$: this part is slightly more tricky to digest, but the logic behind it is that we shouold start from $i$ and add something to it to push the least significant one-bit further. It is beacuse as long as this one-bit goes further, the remaining number would be larger than $i$ after removing it. To push this one-bit further, we can add the value of the least significant one-bit to it: $[(i + LSOne(i)), (i + LSOne(i) + LSOne(i + LSOne(i))), …]$

The complexity? again $O(log n)$.

Simple Implementation

The implementation is taken from the book Competitive Programmingn book 1, by Steven and Felix Halim and Suhendry Effendy.


#define LSOne(S)   ((S) & (-S))
typedef vector<int> vi;

class FenwickTree {
private:
    vi ft;

public:
    FenwickTree(int n) {
        ft.assign(n + 1, 0);  // Fenwick Tree is 1-based index, so size n+1
    }

    // Function to update the Fenwick Tree with a new value at index idx
    void update(int i, int value) {
        while (idx <= n) {
            ft[idx] += value;
            i += LSOne(i);  // Move to the next responsible node
        }
    }

    // Function to compute the prefix sum from index 1 to idx
    int query(int i) {
        int sum = 0;
        while (i > 0) {
            sum += ft[i];
            i -= LSOne(i);  // Move to the parent node
        }
        return sum;
    }

    // Function to get the sum in the range [l, r]
    int rsqe(int i, int j) {
        return query(i) - query(i - 1);
    }
};

Things to still add: Other operations that can be done on Fenwick Tree, their complexity, and the complete implementation.

]]>
Pegah Khayatan
Blog Post number 32014-08-14T00:00:00-07:002014-08-14T00:00:00-07:00https://pegah-kh.github.io/posts/2014/08/blog-post-3This is a sample blog post. Lorem ipsum I can’t remember the rest of lorem ipsum and don’t have an internet connection right now. Testing testing testing this blog post. Blog posts are cool.

Headings are cool

You can have many headings

Aren’t headings cool?

]]>
Pegah Khayatan
Blog Post number 22013-08-14T00:00:00-07:002013-08-14T00:00:00-07:00https://pegah-kh.github.io/posts/2013/08/blog-post-2This is a sample blog post. Lorem ipsum I can’t remember the rest of lorem ipsum and don’t have an internet connection right now. Testing testing testing this blog post. Blog posts are cool.

Headings are cool

You can have many headings

Aren’t headings cool?

]]>
Pegah Khayatan