20 Classic Redis Interview Questions and Answers
This article compiles 20 classic Redis interview questions covering its definition, data structures, performance mechanisms, caching challenges, high‑availability setups, persistence options, distributed locking techniques, and best‑practice solutions, providing developers with comprehensive insights into Redis architecture and practical usage.
Preface
With the busy season approaching, we have organized 20 classic Redis interview questions to help everyone.
1. What is Redis and what is it used for?
Redis (Remote Dictionary Server) is an open‑source, ANSI‑C written, network‑enabled, in‑memory (with optional persistence) key‑value database that provides APIs for many languages.
Unlike MySQL, Redis stores data in memory, offering read/write speeds of over 100,000 operations per second, making it widely used for caching, distributed locks, transactions, persistence, Lua scripting, LRU eviction, and various clustering solutions.
2. Basic Redis data structures
Redis provides five primary data types:
String
Hash
List
Set
Zset (sorted set)
It also has three special types:
Geospatial
HyperLogLog
Bitmap
2.1 String
Overview: binary‑safe, can store images or serialized objects, max size 512 MB.
Simple usage: set key value , get key
Use cases: shared session, distributed lock, counters, rate limiting.
Internal encoding: int (8‑byte integer), embstr (≤39 bytes), raw (>39 bytes).
Redis uses SDS (Simple Dynamic String) instead of C's char[] . The SDS header is defined as:
struct sdshdr{
unsigned int len; // length of buffer
unsigned int free; // free space in buffer
char buf[]; // actual data
}Reason for SDS: O(1) length retrieval versus O(n) for C strings.
2.2 Hash
Overview: a value that itself is a key‑value map.
Simple usage: hset key field value , hget key field
Internal encoding: ziplist (compressed list) or hashtable .
Use case: caching user information.
Note: using hgetall on large hashes can block; prefer hscan or hmget for partial fields.
2.3 List
Overview: ordered collection of strings, up to 2^32‑1 elements.
Simple usage: lpush key value [value ...] , lrange key start end
Internal encoding: ziplist or linkedlist .
Use cases: message queues, article lists.
2.4 Set
Overview: unordered collection of unique strings.
Simple usage: sadd key element [element ...] , smembers key
Internal encoding: intset (integer set) or hashtable .
Note: smembers , lrange , hgetall can be heavy; use sscan for large sets.
Use cases: user tags, random draws, social features.
2.5 Sorted Set (Zset)
Overview: ordered set of unique strings with scores.
Simple usage: zadd key score member [score member ...] , zrank key member
Internal encoding: ziplist for small sets, skiplist for larger ones.
Use cases: leaderboards, social likes.
2.6 Special data structures
Geospatial – location indexing (Redis 3.2+).
HyperLogLog – cardinality estimation.
Bitmap – bit‑level mapping for massive boolean flags.
3. Why is Redis so fast?
3.1 Memory‑based storage
Memory reads/writes are far faster than disk I/O, eliminating the disk bottleneck.
3.2 Efficient data structures
Redis uses specialized structures such as SDS, hash tables, and skip lists, which provide O(1) or O(log N) operations.
SDS advantages
O(1) string length retrieval.
Pre‑allocation reduces frequent reallocations.
Lazy free space reuse.
Binary‑safe storage.
Dictionary (hash table)
Key‑value pairs are stored in a hash table, offering O(1) lookup.
Skip list
Provides average O(log N) search with multi‑level indexing.
3.3 Reasonable data encoding
String: int for numbers, embstr ≤39 bytes, raw otherwise.
List: ziplist if < 512 elements and each < 64 bytes; otherwise linkedlist .
Hash: ziplist if < 512 fields and values < 64 bytes; else hashtable .
Set: intset for small integer sets; else hashtable .
Zset: ziplist if < 128 elements and each < 64 bytes; else skiplist .
3.4 Thread model
I/O multiplexing – Redis uses epoll to handle many connections in a single thread.
Single‑threaded command execution – avoids context switches and lock contention, though long‑running commands can block.
Redis 6.0 introduced optional worker threads for I/O and protocol parsing, while command execution remains single‑threaded.
3.5 Virtual memory mechanism
Cold data can be swapped to disk, freeing memory for hot data, with lazy eviction when memory pressure occurs.
4. Cache problems
4.1 Cache penetration
Queries for non‑existent data repeatedly hit the database because the cache never stores a placeholder.
Mitigation:
Validate request parameters at the API layer.
Cache null or default values with an expiration.
Use a Bloom filter to pre‑check existence.
4.2 Cache avalanche
Massive simultaneous expiration causes a surge of DB traffic.
Stagger expiration times (add random offset).
Deploy high‑availability Redis clusters.
4.3 Cache breakdown (hot key)
When a hot key expires, a flood of concurrent requests hits the DB.
Solutions:
Mutex lock (e.g., SETNX ) to ensure only one request rebuilds the cache.
“Never expire” – keep the key indefinitely and refresh asynchronously.
5. Hot key problem
Hot keys receive extremely high request rates, potentially overwhelming a single Redis node.
Identification methods:
Experience‑based judgment.
Client‑side statistics.
Proxy‑layer monitoring.
Mitigations:
Scale the cluster (add shards/replicas).
Distribute hot keys across nodes.
Use a second‑level cache (e.g., local JVM cache).
6. Expiration and eviction policies
6.1 Expiration strategies
Passive (lazy) expiration – keys are removed only when accessed.
Active (periodic) expiration – Redis randomly samples a subset of keys every 100 ms and deletes expired ones.
Timer‑based expiration – a timer per key removes it exactly at TTL, but is CPU‑intensive.
Redis combines lazy and periodic expiration.
6.2 Memory eviction policies
volatile-lru
allkeys-lru
volatile-lfu
allkeys-lfu
volatile-random
allkeys-random
volatile-ttl
noeviction
7. Common Redis use cases
Cache
Leaderboard
Counter
Shared session
Distributed lock
Social graph
Message queue
Bit operations
7.1 Cache
Improves response speed and reduces DB load; richer data types and persistence make it superior to Memcached.
7.2 Leaderboard
Uses ZSET to store scores; example commands:
zadd user:ranking:2021-03-03 Jay 3 zincrby user:ranking:2021-03-03 Jay 1 zrem user:ranking:2021-03-03 John zrevrange user:ranking:2021-03-03 0 27.3 Counter
Atomic increments ( INCR ) provide high‑throughput counting for views, plays, etc.
7.4 Shared session
Centralizes session data across stateless web servers.
7.5 Distributed lock
Implemented via SETNX or the extended SET key value NX EX ttl pattern.
7.6 Social features
Likes, followers, and feeds map naturally to sets, sorted sets, and hashes.
7.7 Message queue
Redis Pub/Sub and blocking list commands enable simple queueing, though not a full replacement for dedicated MQs.
7.8 Bit operations
Bitmaps efficiently store billions of boolean flags (e.g., daily sign‑in).
8. Persistence mechanisms
8.1 RDB (snapshot)
Periodically writes a compressed snapshot ( dump.rdb ) to disk; fast recovery but not real‑time.
8.2 AOF (append‑only file)
Logs every write operation; provides better durability at the cost of larger files and slower recovery.
9. High availability
9.1 Master‑slave replication
Full sync via BGSAVE creates an RDB snapshot; subsequent writes are streamed to slaves.
9.2 Sentinel
Monitors masters and slaves, performs automatic failover, and notifies clients.
9.3 Cluster
Shards data across 16384 hash slots; uses Gossip protocol for node communication and supports automatic failover with replicas.
Hash slot algorithm
Key → CRC16 → slot (0‑16383); each node owns a subset of slots.
Failover process
Nodes vote to mark a master as objectively down, then promote a replica.
10. Distributed lock implementations
10.1 SETNX + EXPIRE (separate)
if (jedis.setnx(key, lockValue) == 1) {
expire(key, 100);
try { /* business */ } finally { jedis.del(key); }
}Risk: if the process crashes between SETNX and EXPIRE , the lock never expires.
10.2 SETNX with timestamp value
long expires = System.currentTimeMillis() + ttl;
if (jedis.setnx(key, String.valueOf(expires)) == 1) return true;
String cur = jedis.get(key);
if (cur != null && Long.parseLong(cur) < System.currentTimeMillis()) {
String old = jedis.getSet(key, String.valueOf(expires));
if (old != null && old.equals(cur)) return true;
}
return false;Problems: requires synchronized clocks, no owner identifier, possible race on expiration.
10.3 SET with NX EX
if (jedis.set(key, lockValue, "NX", "EX", 100) == 1) { /* business */ jedis.del(key); }May still suffer from lock expiration before business finishes.
10.4 SET with unique value + Lua unlock
if (jedis.set(key, uuid, "NX", "EX", 100) == 1) { /* business */ }
-- Lua script for safe unlock
if redis.call('get', KEYS[1]) == ARGV[1] then
return redis.call('del', KEYS[1])
else
return 0
endEnsures only the lock owner can release.
11. Redisson
Redisson adds a watchdog thread that automatically extends the lock TTL while the owning thread is still active, preventing premature expiration.
12. Redlock algorithm
Uses multiple independent Redis masters (e.g., 5). A client must acquire the lock on at least a majority (N/2+1) within a timeout shorter than the lock TTL. If successful, the effective TTL is reduced by the time spent acquiring the lock. On failure, the client releases any partial locks.
13. Skip list (used by ZSET)
Provides O(log N) average search, O(N) worst‑case, and supports range queries.
14. MySQL‑Redis consistency
14.1 Delayed double delete
Delete cache, update DB, then delete cache again after a short sleep (≈ DB read time + a few hundred ms).
14.2 Delete‑retry via message queue
If cache deletion fails, enqueue the key for asynchronous retry.
14.3 Binlog‑based async deletion
Consume MySQL binlog (e.g., via Canal) and delete related cache entries.
15. Why Redis 6.0 added multithreading?
To offload network I/O and protocol parsing to worker threads, while command execution remains single‑threaded, thus improving throughput on I/O‑bound workloads.
16. Transactions
Commands MULTI , EXEC , WATCH provide atomic execution of a command queue.
17. Hash collisions
Redis resolves collisions with chaining; rehashing expands the hash table and uses a secondary table during migration.
18. RDB generation while serving requests
SAVE blocks the server; BGSAVE forks a child process to write the snapshot, allowing the parent to continue handling clients.
19. Protocol
Redis uses RESP (Redis Serialization Protocol), a simple, fast, and human‑readable protocol.
20. Bloom filter
A space‑efficient probabilistic data structure for membership testing, useful to mitigate cache penetration. It uses multiple hash functions and a bit array; false positives are possible but false negatives are not.
Code Ape Tech Column
Former Ant Group P8 engineer, pure technologist, sharing full‑stack Java, job interview and career advice through a column. Site: java-family.cn
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.