0% found this document useful (0 votes)
2 views10 pages

Java Formulas

The document provides a comprehensive overview of various algorithms and data structures in Java, focusing on fast input/output techniques, graph algorithms, dynamic programming patterns, and bit manipulation. It includes code snippets and explanations for tree dynamic programming, graph traversal methods, and common dynamic programming transitions. Additionally, it covers advanced topics like SOS DP and bitmask DP, making it a useful reference for competitive programming.
Copyright
© All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
2 views10 pages

Java Formulas

The document provides a comprehensive overview of various algorithms and data structures in Java, focusing on fast input/output techniques, graph algorithms, dynamic programming patterns, and bit manipulation. It includes code snippets and explanations for tree dynamic programming, graph traversal methods, and common dynamic programming transitions. Additionally, it covers advanced topics like SOS DP and bitmask DP, making it a useful reference for competitive programming.
Copyright
© All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd

Fast io }

import [Link].*; return [Link]();


import [Link].*; }
}
public class Main {
static class FastScanner { public static void main(String[] args) throws
private final byte[] buffer = new byte[1 << Exception {
16]; FastScanner fs = new
private int ptr = 0, len = 0; FastScanner([Link]);
private final InputStream in; StringBuilder out = new StringBuilder();

FastScanner(InputStream in) { int t = 1; // [Link]();


[Link] = in; while (t-- > 0) {
} // solve here
}
int read() throws IOException {
if (ptr >= len) { [Link]([Link]());
len = [Link](buffer); }
ptr = 0; }
if (len <= 0) return -1;
} Math utilities
return buffer[ptr++]; static long gcd(long a, long b) {
} return b == 0 ? a : gcd(b, a % b);
}
int nextInt() throws IOException {
int c, sgn = 1, res = 0; static long lcm(long a, long b) {
do { c = read(); } while (c <= ' '); return a / gcd(a, b) * b;
if (c == '-') { sgn = -1; c = read(); } }
while (c > ' ') {
res = res * 10 + (c - '0'); static long mod = 1_000_000_007;
c = read();
} static long modPow(long a, long e) {
return res * sgn; long r = 1;
} while (e > 0) {
if ((e & 1) == 1) r = r * a % mod;
long nextLong() throws IOException { a = a * a % mod;
int c, sgn = 1; e >>= 1;
long res = 0; }
do { c = read(); } while (c <= ' '); return r;
if (c == '-') { sgn = -1; c = read(); } }
while (c > ' ') {
res = res * 10 + (c - '0'); Arrays & Prefix
c = read(); long[] pref = new long[n + 1];
} for (int i = 0; i < n; i++)
return res * sgn; pref[i + 1] = pref[i] + arr[i];
}
// sum l..r (0-indexed)
String next() throws IOException { long sum = pref[r + 1] - pref[l];
int c;
StringBuilder sb = new StringBuilder(); Graph (Adj List + DFS/BFS)
do { c = read(); } while (c <= ' '); ArrayList<Integer>[] g = new ArrayList[n];
while (c > ' ') { for (int i = 0; i < n; i++) g[i] = new ArrayList<>();
[Link]((char) c);
c = read(); boolean[] vis = new boolean[n];
dfs1(v, u);
void dfs(int u) { sub[u] += sub[v];
vis[u] = true; }
for (int v : g[u])
}
if (!vis[v]) dfs(v);
}
void dfs2(int u, int p) {
Queue<Integer> q = new ArrayDeque<>(); for (int v : g[u]) {
[Link](src); if (v == p) continue;
vis[src] = true;
sub[u] -= sub[v];
while (![Link]()) {
sub[v] += sub[u];
int u = [Link]();
for (int v : g[u]) {
if (!vis[v]) { dfs2(v, u);
vis[v] = true;
[Link](v); sub[v] -= sub[u];
} sub[u] += sub[v];
}
}
}
}

TREE DP PATTERNS (Java) 3️⃣ DP with 2 states (take / not take)

1️⃣ Subtree DP (bottom-up) Classic tree independent set

dp[u] depends on children int[][] dp; // dp[u][0/1]

ArrayList<Integer>[] g; void dfs(int u, int p) {


int[] dp; dp[u][0] = 0;
dp[u][1] = 1;
void dfs(int u, int p) {
dp[u] = 1; // base for (int v : g[u]) {
for (int v : g[u]) { if (v == p) continue;
if (v == p) continue; dfs(v, u);
dfs(v, u); dp[u][0] +=
dp[u] += dp[v]; // example: [Link](dp[v][0], dp[v][1]);
subtree size dp[u][1] += dp[v][0];
} }
} }

2️⃣ Rerooting DP 4️⃣ Tree diameter (2 DFS trick)


int far, dist;
compute dp for all roots void dfs(int u, int p, int d) {
if (d > dist) { dist = d; far =
int[] sub, ans; u; }
for (int v : g[u])
void dfs1(int u, int p) { if (v != p) dfs(v, u, d +
sub[u] = 1; 1);
for (int v : g[u]) { }
if (v == p) continue; // dfs(0,-1,0); dfs(far,-1,0);
}

🌐 GRAPH PATTERNS }

4️⃣ Dijkstra (weighted graph)


1️⃣ BFS shortest path (unweighted)
long[] dist = new long[n];
int[] dist = new int[n];
[Link](dist, Long.MAX_VALUE);
[Link](dist, -1);
PriorityQueue<long[]> pq = new
Queue<Integer> q = new
PriorityQueue<>([Link]
ArrayDeque<>();
Long(a -> a[0]));

dist[s] = 0;
dist[s] = 0;
[Link](s);
[Link](new long[]{0, s});

while (![Link]()) {
while (![Link]()) {
int u = [Link]();
long[] cur = [Link]();
for (int v : g[u]) {
long d = cur[0];
if (dist[v] == -1) {
int u = (int) cur[1];
dist[v] = dist[u] + 1;
if (d != dist[u]) continue;
[Link](v);
}
for (long[] e : g[u]) {
}
int v = (int) e[0];
}
long w = e[1];
if (dist[v] > d + w) {
2️⃣ DFS cycle detection (undirected)
dist[v] = d + w;
boolean dfs(int u, int p) { [Link](new
vis[u] = true; long[]{dist[v], v});
for (int v : g[u]) { }
if (v == p) continue; }
if (vis[v] || dfs(v, u)) }
return true;
} 🧠 BIT OPERATIONS (VERY IMPORTANT)
return false;
} 1️⃣ Basics
x & 1 // check odd
3️⃣ Topological Sort (DAG) x << k // multiply by 2^k
int[] indeg = new int[n]; x >> k // divide by 2^k
Queue<Integer> q = new x & (x - 1) // remove lowest set
ArrayDeque<>(); bit

for (int i = 0; i < n; i++) 2️⃣ Check / Set / Unset bit


if (indeg[i] == 0) [Link](i); boolean on = ((mask >> i) & 1) == 1;
mask |= (1 << i); // set
while (![Link]()) { mask &= ~(1 << i); // unset
int u = [Link](); mask ^= (1 << i); // toggle
for (int v : g[u]) {
if (--indeg[v] == 0) 3️⃣ Iterate over all subsets
[Link](v);
for (int sub = mask; sub > 0; sub = Space optimized:​
(sub - 1) & mask) { dp[w] = max(dp[w], dp[w - wi] + vi)
// sub is subset of mask
} ▶ Unbounded Knapsack
dp[w] = max(dp[w], dp[w - wi] + vi)
4️⃣ Count set bits
int c = [Link](x); ▶ Grid DP
dp[i][j] = dp[i-1][j] + dp[i][j-1]
5️⃣ Bitmask DP (subset DP)
int N = 1 << n; With obstacle:​
if blocked → dp = 0
int[] dp = new int[N];
[Link](dp, INF);
dp[0] = 0; 3️⃣ Subsequence / String DP​
for (int mask = 0; mask < N; mask++) ▶ LCS
{ if s[i]==t[j]:
for (int i = 0; i < n; i++) { dp[i][j] = dp[i-1][j-1] + 1
if ((mask & (1 << i)) == 0) else:
{ dp[i][j] = max(dp[i-1][j],
dp[mask | (1 << i)] = dp[i][j-1])
[Link](dp[mask | ▶ Edit Distance
(1 << i)], dp[mask] + cost[i]); dp[i][j] = min(
} dp[i-1][j] + 1, // delete
} dp[i][j-1] + 1, // insert
} dp[i-1][j-1] + cost //
replace
📘 COMMON DP TRANSITION FORMULAS )
(CP CHEAT SHEET)
4️⃣ Interval DP​
1️⃣ 1D DP (Linear)
▶ Merge / Split

▶ Take / Skip dp[l][r] = min over k in [l,r):


dp[l][k] + dp[k+1][r] +
dp[i] = max(dp[i-1], dp[i-2] + a[i])
👉 House robber, no adjacent
cost(l,r)​
👉 Matrix chain, stone merging

▶ Prefix choice​
▶ Game DP
dp[i] = min over j<i (dp[j] +
cost(j+1..i)) dp[l][r] = max(
a[l] - dp[l+1][r],
▶ Count ways a[r] - dp[l][r-1]
)​
dp[i] = dp[i-1] + dp[i-2]

5️⃣ Tree DP (Recap)​
​ ▶ Combine children
2️⃣ 2D DP (Classic) dp[u] = base
for v in children:
▶ Knapsack (0/1) dp[u] = combine(dp[u], dp[v])
dp[i][w] = max(dp[i-1][w],
dp[i-1][w - wi] + vi) ▶ Two states (pick / not pick)
dp[u][1] = val[u] + Σ dp[v][0]
dp[u][0] = Σ max(dp[v][0], dp[v][1]) int bit = xr & -xr;
int x = 0, y = 0;
6️⃣ Bitmask DP​
▶ Add element for (int v : a) {
if ((v & bit) != 0) x ^= v;
dp[mask | (1<<i)] =
else y ^= v;
min(dp[mask | (1<<i)],
}
dp[mask] + cost[i])
return new int[]{x, y};
▶ Traveling Salesman }

dp[mask][u] =
min over v in mask: 4️⃣ Count Set Bits
dp[mask ^ (1<<u)][v] + int c = [Link](x);
dist[v][u] int c2 = [Link](y);

7️⃣ LIS (Important Pattern) 5️⃣ XOR from 1 to N


dp[i] = 1 + max(dp[j]) for all j<i static long xor1toN(long n) {
with a[j]<a[i] if (n % 4 == 0) return n;
if (n % 4 == 1) return 1;
Optimized:​ if (n % 4 == 2) return n + 1;
tails[k] = min ending value of LIS return 0;
length k }

8️⃣ Counting DP (Mod)​


dp[i] = (dp[i] + dp[j]) % MOD 6️⃣ Subarrays with XOR = K
static long countXorSubarrays(int[]

⚙️ BIT MANIPULATION — JAVA


​ a, int k) {
HashMap<Integer, Integer> map =
IMPLEMENTATIONS​
new HashMap<>();
1️⃣ Power of Two​
[Link](0, 1);
static boolean isPowerOfTwo(long x)
{​
int pref = 0;
return x > 0 && (x & (x - 1)) ==
long ans = 0;
0;​
}​
for (int v : a) {

2️⃣ Single Number (others twice)​ pref ^= v;
static int singleNumber(int[] a) {​ ans += [Link](pref
int x = 0;​ ^ k, 0);
for (int v : a) x ^= v;​ [Link](pref,
return x;​ [Link](pref, 0) + 1);
} }
return ans;
}
3️⃣ Two Unique Numbers (others twice)
static int[] twoUnique(int[] a) {
7️⃣ Maximum XOR Pair (Binary Trie)
int xr = 0;
for (int v : a) xr ^= v; static class Trie {
Trie[] ch = new Trie[2]; for (int y : cur) [Link](y &
} x); // OR: y | x
cur = next;
static void insert(Trie root, int x)
{ for (int v : cur) {
Trie cur = root; // count / compare v
for (int i = 31; i >= 0; i--) { }
int b = (x >> i) & 1; }
if ([Link][b] == null)
[Link][b] = new Trie(); 9️⃣ Bitmask DP Template
cur = [Link][b];
int N = 1 << n;
}
int[] dp = new int[N];
}
[Link](dp, INF);
dp[0] = 0;
static int maxXor(Trie root, int x)
{
for (int mask = 0; mask < N; mask++)
Trie cur = root;
{
int ans = 0;
for (int i = 0; i < n; i++) {
for (int i = 31; i >= 0; i--) {
if ((mask & (1 << i)) == 0)
int b = (x >> i) & 1;
{
if ([Link][1 - b] != null) {
int nmask = mask | (1 <<
ans |= (1 << i);
i);
cur = [Link][1 - b];
dp[nmask] =
} else {
[Link](dp[nmask], dp[mask] +
cur = [Link][b];
cost[i]);
}
}
}
}
return ans;
}
}

🔟 SOS DP (Advanced)
Usage:​ int N = 1 << n;
Trie root = new Trie();​
int[] dp = new int[N];
for (int x : a) insert(root, x);​
int res = 0;​
// dp[mask] initialized with base
for (int x : a) res = [Link](res,
values
maxXor(root, x));

for (int i = 0; i < n; i++) {


8️⃣ AND / OR Subarray Trick for (int mask = 0; mask < N;
Set<Integer> cur = new HashSet<>(); mask++) {
long ans = 0; if ((mask & (1 << i)) != 0)
{
for (int x : a) { dp[mask] += dp[mask ^ (1
Set<Integer> next = new << i)];
HashSet<>(); }
[Link](x); }
}
1️⃣1️⃣ Linear XOR Basis ( 🔥 VERY IMPORTANT) [Link](a, b) // double
static class XorBasis { (avoid in mod problems)​
static final int LOG = 60; [Link](x)​
long[] basis = new long[LOG]; [Link](x)​
[Link](x)​
[Link](x)​
⚠️ Prefer manual power for mod, not
void insert(long x) {
for (int i = LOG - 1; i >=
0; i--) { [Link].
if (((x >> i) & 1) == 0)
continue; 🧠 BIT OPERATIONS (Integer / Long)
if (basis[i] == 0) {
basis[i] = x; [Link](x)​
return; [Link](x)​
} [Link](x)​
x ^= basis[i]; [Link](x)​
} [Link](x)​
} [Link](x)

long getMax() { 👉 VERY useful shortcuts:​


long res = 0; int msb = 31 -
for (int i = LOG - 1; i >= [Link](x);​
0; i--) { int lsb =
res = [Link](res, res [Link](x);
^ basis[i]);
}
return res;
📦 ARRAYS ([Link])​
[Link](arr)​
} [Link](arr, value)​
} [Link](arr, key)​
[Link](a, b)​
⚠️ JAVA BIT PITFALLS (MEMORIZE) [Link](arr, n)

●​
●​
Use 1L << i for i ≥ 31
Prefer int for masks, long for XOR
📚 COLLECTIONS
([Link])​
sums
[Link](list)​
●​ HashMap<Integer,Integer> faster
than Long [Link](list)​
●​ Bitmask DP max n ≈ 20 [Link](list)​
[Link](list)​
[Link](list, x)
JAVA INBUILT FUNCTIONS (CP CHEAT
SHEET) 🗂️ MAPS & SETS​
HashMap​
🔢 MATH ([Link]) [Link](k, 0)​
[Link](k, v)​
[Link](x)​ [Link](k, 1, Integer::sum)​
[Link](a, b)​ [Link](k)​
[Link](a, b)​ ​
TreeMap / TreeSet (ordered)​ [Link](a, (x, y) -> x[0] -
firstKey(), lastKey()​ y[0]);
floorKey(x), ceilingKey(x)​
lowerKey(x), higherKey(x)​ // fast swap​
​ a ^= b; b ^= a; a ^= b;​
🧵 STRING ([Link])​ ​
[Link]()​ Sort int[][] by first column
[Link](i)​ (ascending)​
[Link](l, r)​ [Link](arr, (a, b) ->
[Link](t)​ [Link](a[0], b[0]));​
[Link](t)​ ​
[Link]() Sort int[][] by first column
(descending)​

✂️ STRINGBUILDER​ [Link](arr, (a, b) ->


[Link](b[0], a[0]));
StringBuilder sb = new
StringBuilder();​
Given an integer array nums, return true if
[Link](x);​ you can partition the array into two subsets
[Link](0); // clear​ such that the sum of the elements in both
subsets is equal or false otherwise.
[Link]();
int n=[Link];
🧮 PRIORITY QUEUE​ int sum=0;
for(int i=0;i<n;i++)
PriorityQueue<Integer> pq = new sum+=nums[i];
PriorityQueue<>(); // min heap​ if(sum%2==1) return false;
sum=sum/2;
PriorityQueue<Integer> pq = new
boolean dp[][]=new
PriorityQueue<>([Link] boolean[n][sum+1];
rder()); //​ for(int i=0;i<n;i++)
dp[i][0]=true;
max heap
if(nums[0]<=sum)
dp[0][nums[0]]=true;
Custom:​ for(int i=1;i<n;i++)
PriorityQueue<int[]> pq = new {
for(int j=1;j<=sum;j++)
PriorityQueue<>((a, b) -> a[0] - {
b[0]); if(j<nums[i])
dp[i][j]=dp[i-1][j];

🚶 QUEUES & DEQUES​


else
dp[i][j]=dp[i-1][j] ||
dp[i-1][j-nums[i]];
ArrayDeque<Integer> dq = new
}
ArrayDeque<>();​ }
[Link](x);​ return dp[n-1][sum];
[Link](x);​
You are given an array 'arr' of size 'n'
[Link]();​
containing positive integers and a target sum
[Link]();
'k'.

🧪 RANDOM (HASHING / STRESS)​ Find the number of ways of selecting the


elements from the array such that the sum of
Random rng = new Random();​
chosen elements is equal to the target 'k'.
[Link](n);​

// sort pairs​
Since the number of ways can be very large, for(int j=0;j<=k;j++)
print it modulo 10 ^ 9 + 7.​ {
if(nums[i]>j)
int n=[Link]; dp[i][j]=dp[i-1][j];
int MOD = 1_000_000_007; else
long dp[][]=new dp[i][j]=dp[i-1][j] +
long[n][tar+1]; dp[i-1][j-nums[i]];
dp[0][0]=(num[0]==0)?2:1; }
if(num[0]!=0 && num[0]<=tar) }
dp[0][num[0]]=1; return dp[n-1][k];
for(int i=1;i<n;i++)
{ Input: amount = 5, coins = [1,2,5]
for(int j=0;j<=tar;j++) Output: 4
{ Explanation: there are four ways to make up
if(num[i]>j) the amount:
dp[i][j]=dp[i-1][j]%MOD; 5=5
else 5=2+2+1
dp[i][j]=(dp[i-1][j]+dp[i-1][j-num[i 5=2+1+1+1
]])%MOD; 5=1+1+1+1+1
} int n=[Link];
} int dp[][]=new
return (int)dp[n-1][tar]; int[n][amount+1];
for(int i=0;i<n;i++)
Input: nums = [1,1,1,1,1], target = 3 dp[i][0]=1;
Output: 5 for(int i=1;i<amount+1;i++)
Explanation: There are 5 ways to assign {
symbols to make the sum of nums be target if(i%coins[0]==0)

3. dp[0][i]=1;
}
-1 + 1 + 1 + 1 + 1 = 3
for(int i=1;i<n;i++)
+1 - 1 + 1 + 1 + 1 = 3
{
+1 + 1 - 1 + 1 + 1 = 3
for(int
+1 + 1 + 1 - 1 + 1 = 3
j=1;j<=amount;j++)
+1 + 1 + 1 + 1 - 1 = 3
{
int n=[Link];
if(coins[i]>j)
int sum=0;
dp[i][j]=dp[i-1][j];
for(int i:nums) sum+=i;
else
if((sum+target)%2==1) return
dp[i][j]=dp[i-1][j]+dp[i][j-coins[i]
0;
];
int k=(sum+target)/2;
}
if(k<0) return 0;
}
int dp[][]=new int[n][k+1];
return dp[n-1][amount];
dp[0][0]=nums[0]==0?2:1;
if(nums[0]!=0 && nums[0]<=k)
dp[0][nums[0]]=1; You are given an integer array coins
for(int i=1;i<n;i++) representing coins of different denominations
{ and an integer amount representing a total
amount of money.
Return the fewest number of coins that you if(i+1>j)
need to make up that amount. If that amount dp[i][j]=dp[i-1][j];
of money cannot be made up by any else
combination of the coins, return -1. dp[i][j]=[Link](dp[i-1][j],price[i
]+dp[i][j-(i+1)]);
You may assume that you have an infinite }
number of each kind of coin. }
return dp[n-1][k];
int n=[Link];
int dp[][]=new
int[n][amount+1];
int INF=amount+1;
for(int i=0;i<n;i++)
dp[i][0]=0;
for(int j=1; j<=amount; j++)
if(j % coins[0] == 0)
dp[0][j] = j / coins[0];
else dp[0][j]=INF;
for(int i=1;i<n;i++)
{
for(int
j=1;j<=amount;j++)
{
if(coins[i]>j)
dp[i][j]=dp[i-1][j];
else
dp[i][j]=[Link](dp[i-1][j],1+dp[i]
[j-coins[i]]);
}
}
return dp[n-1][amount]>=INF
? -1 : dp[n-1][amount];

Rodcutting​
int n=[Link];
int dp[][]=new int[n][k+1];
for(int i=0;i<n;i++)
dp[i][0]=0;
for(int i=0;i<=k;i++)
{
dp[0][i]=i*price[0];
}
for(int i=1;i<n;i++)
{
for(int j=1;j<=k;j++)
{

You might also like