最可靠方法是执行select table_name from information_schema.tables where table_schema = 'your_db_name' and table_type = 'base table',需显式指定数据库名且过滤基础表,避免依赖database()函数或大小写错误。

怎么从 INFORMATION_SCHEMA.TABLES 查表名
直接查 INFORMATION_SCHEMA.TABLES 是最通用的方式,几乎所有支持 SQL 标准的数据库(MySQL、PostgreSQL、SQL Server、SQLite 3.25+)都提供这个视图。但注意:不同数据库对 schema 名、table_type 的字段名和值有差异。
核心语句长这样:
SELECT table_name FROM INFORMATION_SCHEMA.TABLES WHERE table_schema = 'public' AND table_type = 'BASE TABLE';
- PostgreSQL 默认 schema 是
public,MySQL 里table_schema对应数据库名,得填你当前库名(比如'mydb') -
table_type值不统一:MySQL 用'BASE TABLE',PostgreSQL 也是;SQL Server 还要排除'VIEW';SQLite 不支持该字段,得换方式 - 权限不足时会返回空结果——不是没表,是没权限读
INFORMATION_SCHEMA
MySQL 下为什么查不到自己建的表
常见原因是 table_schema 条件写错了。MySQL 把数据库名当 schema,如果你在名为 test_db 的库中执行查询,必须显式指定:
SELECT table_name FROM INFORMATION_SCHEMA.TABLES WHERE table_schema = 'test_db' AND table_type = 'BASE TABLE';
- 别用
CURRENT_SCHEMA()或DATABASE()函数动态取值——部分客户端或低版本 MySQL 不支持在 WHERE 中用它们 - 如果表是 InnoDB 引擎但属于系统库(如
mysql、performance_schema),默认被过滤掉,需确认是否真想查那些 - 大小写敏感:Linux 上
table_schema值是小写的,写成'TEST_DB'就匹配不上
PostgreSQL 中如何只查用户表、跳过系统表
PostgreSQL 的 INFORMATION_SCHEMA.TABLES 默认包含所有 schema,包括 pg_catalog 和 information_schema 自身。真正干净的做法是加 schema 过滤:
SELECT table_name FROM INFORMATION_SCHEMA.TABLES WHERE table_schema = 'public' AND table_type = 'BASE TABLE';
- 除非你明确需要其他 schema(比如
myschema),否则别省略table_schema = 'public' - 用
\dt(psql 命令)验证结果是否一致——它底层也查系统目录,但更可靠 - 如果创建表时指定了 schema(如
CREATE TABLE myschema.users),就必须把myschema写进条件,不能只依赖public
SQLite 怎么办:它没有 INFORMATION_SCHEMA
SQLite 3.25 之前压根没 INFORMATION_SCHEMA,得查系统表 sqlite_master:
SELECT name FROM sqlite_master WHERE type = 'table' AND name NOT LIKE 'sqlite_%';
-
NOT LIKE 'sqlite_%'是为了排除内部表(如sqlite_sequence),但自定义表名若以sqlite_开头也会被误杀——这是硬伤,没法靠标准方式规避 - SQLite 不区分 schema,所以不用管
table_schema字段 - 如果用了 ATTACH 加载了多个数据库,
sqlite_master只返回主库的表;要查附加库,得用附加库名.sqlite_master(如aux.sqlite_master)
跨数据库兼容性最麻烦的地方就在这儿:不是语法写错,而是根本没那个表可查。动手前先 SELECT sqlite_version(); 确认版本,比反复试错快得多。










