Cassandra数据类型 #
一、数据类型概述 #
Cassandra提供了丰富的数据类型,可以分为以下几类:
text
Cassandra数据类型
├── 基本类型
│ ├── 数值类型
│ ├── 文本类型
│ ├── 时间类型
│ └── 其他类型
├── 集合类型
│ ├── List
│ ├── Set
│ └── Map
├── 用户定义类型
│ └── UDT
└── 特殊类型
├── Counter
├── Tuple
└── Frozen
二、基本数据类型 #
2.1 数值类型 #
| 类型 | 描述 | 范围 | 示例 |
|---|---|---|---|
| TINYINT | 8位有符号整数 | -128 到 127 | TINYINT |
| SMALLINT | 16位有符号整数 | -32,768 到 32,767 | SMALLINT |
| INT | 32位有符号整数 | -2^31 到 2^31-1 | INT |
| BIGINT | 64位有符号整数 | -2^63 到 2^63-1 | BIGINT |
| VARINT | 任意精度整数 | 无限制 | VARINT |
| FLOAT | 32位浮点数 | IEEE 754 | FLOAT |
| DOUBLE | 64位浮点数 | IEEE 754 | DOUBLE |
| DECIMAL | 高精度十进制 | 无限制 | DECIMAL |
sql
-- 创建包含数值类型的表
CREATE TABLE numeric_example (
id UUID PRIMARY KEY,
tiny_val TINYINT,
small_val SMALLINT,
int_val INT,
big_val BIGINT,
var_val VARINT,
float_val FLOAT,
double_val DOUBLE,
decimal_val DECIMAL
);
-- 插入数据
INSERT INTO numeric_example (
id, tiny_val, small_val, int_val, big_val,
var_val, float_val, double_val, decimal_val
) VALUES (
uuid(), 100, 30000, 2000000000, 9000000000000000000,
123456789012345678901234567890, 3.14, 3.14159265358979, 3.14159265358979323846
);
2.2 文本类型 #
| 类型 | 描述 | 最大长度 | 示例 |
|---|---|---|---|
| TEXT | UTF-8编码字符串 | 2GB | TEXT |
| VARCHAR | 同TEXT | 2GB | VARCHAR |
| ASCII | ASCII字符串 | 2GB | ASCII |
sql
-- 创建包含文本类型的表
CREATE TABLE text_example (
id UUID PRIMARY KEY,
name TEXT,
description VARCHAR,
code ASCII
);
-- 插入数据
INSERT INTO text_example (id, name, description, code)
VALUES (
uuid(),
'张三',
'这是一个很长的描述文本...',
'ABC123'
);
-- 字符串函数
SELECT
name,
length(name) as name_length,
lower(name) as name_lower,
upper(name) as name_upper
FROM text_example;
2.3 时间类型 #
| 类型 | 描述 | 格式 | 示例 |
|---|---|---|---|
| TIMESTAMP | 时间戳 | 毫秒精度 | 2024-01-15 10:30:00.000 |
| DATE | 日期 | YYYY-MM-DD | 2024-01-15 |
| TIME | 时间 | HH:MM:SS.mmm | 10:30:00.000 |
| DURATION | 时间段 | ISO 8601 | P1Y2M3DT4H5M6S |
sql
-- 创建包含时间类型的表
CREATE TABLE time_example (
id UUID PRIMARY KEY,
created_at TIMESTAMP,
birth_date DATE,
work_start TIME,
duration_val DURATION
);
-- 插入数据
INSERT INTO time_example (id, created_at, birth_date, work_start, duration_val)
VALUES (
uuid(),
toTimestamp(now()),
'1990-05-20',
'09:00:00.000',
1y2mo3d4h5m6s
);
-- 时间函数
SELECT
created_at,
toDate(created_at) as date_part,
toTime(created_at) as time_part,
toUnixTimestamp(created_at) as unix_ts
FROM time_example;
2.4 其他基本类型 #
| 类型 | 描述 | 示例 |
|---|---|---|
| BOOLEAN | 布尔值 | true/false |
| UUID | 标准UUID | 550e8400-e29b-41d4-a716-446655440000 |
| TIMEUUID | 基于时间的UUID | 自动生成 |
| INET | IP地址 | 192.168.1.1 或 2001:db8::1 |
| BLOB | 二进制数据 | 0x48656c6c6f |
sql
-- 创建包含其他类型的表
CREATE TABLE misc_example (
id UUID PRIMARY KEY,
is_active BOOLEAN,
user_uuid UUID,
time_uuid TIMEUUID,
ip_address INET,
binary_data BLOB
);
-- 插入数据
INSERT INTO misc_example (
id, is_active, user_uuid, time_uuid, ip_address, binary_data
) VALUES (
uuid(),
true,
uuid(),
now(),
'192.168.1.100',
0x48656c6c6f20576f726c64
);
-- UUID函数
SELECT
id,
user_uuid,
time_uuid,
dateOf(time_uuid) as uuid_date,
unixTimestampOf(time_uuid) as uuid_ts
FROM misc_example;
三、集合类型 #
3.1 List(列表) #
List是有序的可重复集合,适合存储有序数据。
sql
-- 创建包含List的表
CREATE TABLE list_example (
user_id UUID PRIMARY KEY,
name TEXT,
tags LIST<TEXT>,
scores LIST<INT>
);
-- 插入数据
INSERT INTO list_example (user_id, name, tags, scores)
VALUES (uuid(), '张三', ['vip', 'active', 'premium'], [85, 90, 78]);
-- 追加元素
UPDATE list_example
SET tags = tags + ['new_tag']
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 前置添加元素
UPDATE list_example
SET tags = ['first'] + tags
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 替换特定位置元素(索引从0开始)
UPDATE list_example
SET tags[0] = 'updated_tag'
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 删除特定元素
UPDATE list_example
SET tags = tags - ['vip']
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 查询
SELECT user_id, tags, tags[0] as first_tag FROM list_example;
3.2 Set(集合) #
Set是无序的唯一值集合,适合存储不重复的数据。
sql
-- 创建包含Set的表
CREATE TABLE set_example (
user_id UUID PRIMARY KEY,
name TEXT,
emails SET<TEXT>,
phone_numbers SET<TEXT>
);
-- 插入数据
INSERT INTO set_example (user_id, name, emails, phone_numbers)
VALUES (uuid(), '李四', {'li@example.com', 'si@example.com'}, {'13800138000'});
-- 添加元素
UPDATE set_example
SET emails = emails + {'new@example.com'}
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 删除元素
UPDATE set_example
SET emails = emails - {'old@example.com'}
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 查询
SELECT user_id, emails FROM set_example;
3.3 Map(映射) #
Map是键值对集合,适合存储属性映射。
sql
-- 创建包含Map的表
CREATE TABLE map_example (
user_id UUID PRIMARY KEY,
name TEXT,
preferences MAP<TEXT, TEXT>,
scores MAP<TEXT, INT>
);
-- 插入数据
INSERT INTO map_example (user_id, name, preferences, scores)
VALUES (
uuid(),
'王五',
{'theme': 'dark', 'language': 'zh', 'timezone': 'Asia/Shanghai'},
{'math': 90, 'english': 85, 'science': 88}
);
-- 添加键值对
UPDATE map_example
SET preferences = preferences + {'notification': 'enabled'}
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 更新特定键
UPDATE map_example
SET preferences['theme'] = 'light'
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 删除键
DELETE preferences['language']
FROM map_example
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 查询特定键值
SELECT user_id, preferences['theme'] as theme FROM map_example;
-- 查询所有键或值
SELECT user_id, keys(preferences), values(preferences) FROM map_example;
3.4 集合类型限制 #
sql
-- 集合类型有以下限制:
-- 1. 单个集合项最大64KB
-- 2. 集合不适合存储大量数据(建议不超过1000个元素)
-- 3. 查询集合内部需要读取整个集合
-- 不推荐:大量数据的集合
-- CREATE TABLE bad_example (
-- user_id UUID PRIMARY KEY,
-- all_history LIST<TEXT> -- 不推荐存储大量历史记录
-- );
-- 推荐:使用分区表存储大量数据
CREATE TABLE user_history (
user_id UUID,
event_time TIMESTAMP,
event_data TEXT,
PRIMARY KEY (user_id, event_time)
) WITH CLUSTERING ORDER BY (event_time DESC);
四、用户定义类型 (UDT) #
4.1 创建UDT #
sql
-- 创建地址类型
CREATE TYPE address (
street TEXT,
city TEXT,
state TEXT,
zip_code TEXT,
country TEXT
);
-- 创建联系方式类型
CREATE TYPE contact (
phone TEXT,
email TEXT,
wechat TEXT
);
-- 创建嵌套UDT
CREATE TYPE full_address (
location address,
contact contact,
is_primary BOOLEAN
);
4.2 使用UDT #
sql
-- 创建使用UDT的表
CREATE TABLE udt_example (
user_id UUID PRIMARY KEY,
name TEXT,
home_address FROZEN<address>,
work_address FROZEN<address>,
full_info FROZEN<full_address>
);
-- 插入数据
INSERT INTO udt_example (user_id, name, home_address)
VALUES (
uuid(),
'赵六',
{street: '朝阳路100号', city: '北京', state: '北京', zip_code: '100000', country: '中国'}
);
-- 更新UDT字段
UPDATE udt_example
SET home_address = {
street: '海淀路200号',
city: '北京',
state: '北京',
zip_code: '100080',
country: '中国'
}
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 更新UDT中的单个字段(需要整体更新)
UPDATE udt_example
SET home_address.city = '上海'
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 查询
SELECT user_id, name, home_address.city FROM udt_example;
4.3 UDT集合 #
sql
-- 创建包含UDT集合的表
CREATE TABLE udt_collection (
user_id UUID PRIMARY KEY,
name TEXT,
addresses LIST<FROZEN<address>>,
contacts MAP<TEXT, FROZEN<contact>>
);
-- 插入数据
INSERT INTO udt_collection (user_id, name, addresses, contacts)
VALUES (
uuid(),
'钱七',
[
{street: '地址1', city: '北京', state: '北京', zip_code: '100000', country: '中国'},
{street: '地址2', city: '上海', state: '上海', zip_code: '200000', country: '中国'}
],
{
'home': {phone: '13800138000', email: 'home@example.com', wechat: 'wx_home'},
'work': {phone: '13900139000', email: 'work@example.com', wechat: 'wx_work'}
}
);
五、特殊类型 #
5.1 Counter(计数器) #
Counter是特殊的64位整数,只能递增或递减。
sql
-- 创建计数器表(只能包含主键和计数器列)
CREATE TABLE counter_example (
user_id UUID PRIMARY KEY,
login_count COUNTER,
page_views COUNTER,
purchase_count COUNTER
);
-- 增加计数
UPDATE counter_example
SET login_count = login_count + 1,
page_views = page_views + 10,
purchase_count = purchase_count + 1
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 减少计数
UPDATE counter_example
SET login_count = login_count - 1
WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
-- 查询
SELECT * FROM counter_example WHERE user_id = 550e8400-e29b-41d4-a716-446655440000;
5.2 Tuple(元组) #
Tuple是固定长度的、有序的、可以包含不同类型的集合。
sql
-- 创建包含Tuple的表
CREATE TABLE tuple_example (
user_id UUID PRIMARY KEY,
name TEXT,
coordinates TUPLE<FLOAT, FLOAT>,
rgb_color TUPLE<INT, INT, INT>,
info TUPLE<TEXT, INT, BOOLEAN>
);
-- 插入数据
INSERT INTO tuple_example (user_id, name, coordinates, rgb_color, info)
VALUES (
uuid(),
'孙八',
(39.9042, 116.4074),
(255, 128, 0),
('描述信息', 100, true)
);
-- 查询
SELECT user_id, coordinates, rgb_color FROM tuple_example;
-- 访问元组元素(从1开始)
SELECT user_id, coordinates.f1 as latitude, coordinates.f2 as longitude
FROM tuple_example;
5.3 Frozen(冻结) #
Frozen用于将复杂类型序列化为单个值。
sql
-- Frozen特点:
-- 1. 整体更新,不能部分更新
-- 2. 可以作为主键的一部分
-- 3. 可以用于UDT、集合、元组
-- 作为主键的一部分
CREATE TABLE frozen_pk_example (
user_id UUID,
address FROZEN<address>,
created_at TIMESTAMP,
PRIMARY KEY (user_id, address)
);
-- Frozen集合
CREATE TABLE frozen_collection (
user_id UUID PRIMARY KEY,
tags FROZEN<SET<TEXT>>,
attributes FROZEN<MAP<TEXT, TEXT>>
);
六、类型转换 #
6.1 显式转换 #
sql
-- CAST函数
SELECT
CAST(age AS BIGINT) as age_bigint,
CAST(price AS TEXT) as price_text,
CAST(score AS DOUBLE) as score_double
FROM products;
-- 类型转换函数
SELECT
blobAsText(textAsBlob('hello')) as text_back,
uuid() as new_uuid,
toDate(now()) as today
FROM system.local;
6.2 JSON转换 #
sql
-- 从JSON创建数据
INSERT INTO users JSON '{
"user_id": "550e8400-e29b-41d4-a716-446655440000",
"name": "JSON用户",
"age": 30,
"tags": ["tag1", "tag2"],
"preferences": {"theme": "dark"}
}';
-- 查询结果转JSON
SELECT toJson(user_id), toJson(name), toJson(tags) FROM users;
-- 完整行转JSON
SELECT toJson(users) FROM users;
七、类型选择建议 #
7.1 数值类型选择 #
| 场景 | 推荐类型 | 原因 |
|---|---|---|
| 年龄 | TINYINT | 范围足够,节省空间 |
| 数量 | INT | 常用范围 |
| ID | BIGINT | 范围大,避免溢出 |
| 精确金额 | DECIMAL | 避免精度丢失 |
| 科学计算 | DOUBLE | 精度高 |
| 大整数 | VARINT | 无限制 |
7.2 时间类型选择 #
| 场景 | 推荐类型 | 原因 |
|---|---|---|
| 创建时间 | TIMESTAMP | 完整时间信息 |
| 生日 | DATE | 只需要日期 |
| 工作时间 | TIME | 只需要时间 |
| 时间段 | DURATION | 表示持续时间 |
| 分布式ID | TIMEUUID | 有序且唯一 |
7.3 集合类型选择 #
| 场景 | 推荐类型 | 原因 |
|---|---|---|
| 有序列表 | LIST | 保持顺序,允许重复 |
| 标签 | SET | 唯一性 |
| 属性映射 | MAP | 键值对 |
| 少量数据 | 集合类型 | 简单方便 |
| 大量数据 | 独立表 | 性能更好 |
八、总结 #
数据类型选择要点:
- 数值类型:根据范围和精度选择合适的类型
- 文本类型:优先使用TEXT,ASCII仅用于纯英文
- 时间类型:TIMESTAMP最常用,TIMEUUID适合分布式ID
- 集合类型:适合少量数据,大量数据用独立表
- UDT:适合结构化数据,提高数据模型可读性
- Counter:专门用于计数场景
下一步,让我们学习Cassandra的分布式架构!
最后更新:2026-03-27