我有一个 SQL Server 2008 数据库,它的数据文件大小约为 2GB,但日志文件超过 8GB。对于 2008 之前的数据库,我可以使用“备份日志”和该TRUNCATE_ONLY选项,但 2008 及更高版本的数据库不再提供此选项。
我确实有一个截断日志文件的脚本:
USE [MyDatabase]
GO
ALTER DATABASE [MyDatabase] SET RECOVERY SIMPLE WITH NO_WAIT
DBCC shrinkfile('MyDatabase_log', 1)
ALTER DATABASE [MyDatabase] SET RECOVERY FULL WITH NO_WAIT
GO
Run Code Online (Sandbox Code Playgroud)
这会完全截断日志文件,但我的问题是:这会影响性能吗?
我每天执行两次完整备份,因此就数据前滚而言,日志实际上不是必需的。
我想要一种方法来确定给定数据库中的哪些列通过 PK/FK 关系连接。我可以通过以下方式返回给定表的 PK/FK 信息
SELECT *
FROM INFORMATION_SCHEMA.KEY_COLUMN_USAGE AS cu
WHERE EXISTS (
SELECT tc.*
FROM INFORMATION_SCHEMA.TABLE_CONSTRAINTS AS tc
WHERE tc.CONSTRAINT_CATALOG = 'MyDatabase'
AND tc.TABLE_NAME = 'MyTable'
/*AND tc.CONSTRAINT_TYPE = 'PRIMARY KEY'*/
AND tc.CONSTRAINT_NAME = cu.CONSTRAINT_NAME);
GO
Run Code Online (Sandbox Code Playgroud)
但是对于从这样的查询返回的 PK,我如何建立关联的 FK(假设有一个)?
我知道您还可以通过以下方式获取引用的表:
SELECT CONSTRAINT_NAME = name,
FOREIGN_SCHEMA = OBJECT_SCHEMA_NAME(parent_object_id),
FOREIGN_TABLE = OBJECT_NAME(parent_object_id),
REFERENCED_SCHEMA = OBJECT_SCHEMA_NAME(referenced_object_id),
REFERENCED_TABLE = OBJECT_NAME(referenced_object_id)
FROM sys.foreign_keys
WHERE OBJECT_NAME(referenced_object_id) = 'MyTable';
GO
Run Code Online (Sandbox Code Playgroud)
但我现在正在努力获得明确的列引用。
我正在为 QlikView 创建一个脚本生成器。要生成脚本,我需要约束和关联的链接。我需要任何给定列(如果有)的所有约束信息。
我想构建一个数据库类来保存给定数据库的所有信息。database.table.column.constraints然后将使用该类结构来获取 PK/FK 上不同列之间的匹配。
很明显,有些列只有 FK,在这种情况下,我还想检索相应键的 PK 信息;有些将只有PK,然后我想要相反的。有些当然可以两者兼而有之。
我有一个运行 SQL Server 2008 R2 的相当繁忙的数据库服务器,它具有以下设置:
假设我无法向此服务器添加额外的驱动器,我是否充分利用了可用的配置?或者我应该在这里考虑另一种方案,例如,将日志与数据文件隔离开来?
更新:
对于那些需要更多硬件详细信息的人:
更新 2:
根据我收到的反馈,我似乎有以下可行的选项可供选择 - 我会将赏金奖励给可以告诉我哪个可能是我概述的环境中最好的人:
我目前正在使用 Tortoise SVN 对 .NET Web 应用程序进行源代码控制。将我们的 SQL Server 存储过程引入源代码管理的最佳方法是什么?我目前使用 VS 2010 作为我的开发环境,并使用 SQL Server Data Tools (SSDT) 连接到外部 SQL Server 2008 R2 数据库。
我过去一直在做的是将 procs 保存到 .sql 文件并将这些文件保持在源代码控制之下。我确定一定有比这更有效的方法吗?我可以在 VS2010、SSDT 甚至生产机器上的 SQL Server 上安装扩展吗?
sql-server-2008 source-control sql-server stored-procedures version-control
我们需要每晚在我们的 SQL Server 2008 R2 上做一些报告。计算报告需要几个小时。为了缩短时间,我们预先计算了一个表格。该表是基于 JOINining 12 个相当大(数千万行)的表创建的。
直到几天前,这个聚合表的计算才用了大约 4 个小时。我们的 DBA 将这个大连接拆分为 3 个较小的连接(每个连接 4 个表)。临时结果每次都保存到一个临时表中,供下次join使用。
DBA 增强的结果是,聚合表在 15 分钟内计算完成。我想知道这怎么可能。DBA 告诉我,这是因为服务器必须处理的数据数量较少。换句话说,在大的原始连接中,服务器必须处理比在总和较小的连接中更多的数据。但是,我认为优化器会使用原始大连接有效地执行此操作,自行拆分连接并仅发送下一个连接所需的列数。
他所做的另一件事是在其中一个临时表上创建了索引。但是,我再次认为优化器会在需要时创建适当的哈希表,并更好地优化计算。
我和我们的 DBA 讨论过这个问题,但他自己不确定是什么导致了处理时间的改善。他刚刚提到,他不会责怪服务器,因为计算如此大的数据可能会让人不知所措,而且优化器可能很难预测最佳执行计划...... 我明白这一点,但我想对确切原因有更多明确的答案。
所以,问题是:
什么可能导致大的改善?
将大连接拆分为小连接是标准程序吗?
在多个较小连接的情况下,服务器必须处理的数据量真的更小吗?
这是原始查询:
Insert Into FinalResult_Base
SELECT
TC.TestCampaignContainerId,
TC.CategoryId As TestCampaignCategoryId,
TC.Grade,
TC.TestCampaignId,
T.TestSetId
,TL.TestId
,TSK.CategoryId
,TT.[TestletId]
,TL.SectionNo
,TL.Difficulty
,TestletName = Char(65+TL.SectionNo) + CONVERT(varchar(4),6 - TL.Difficulty)
,TQ.[QuestionId]
,TS.StudentId
,TS.ClassId
,RA.SubjectId
,TQ.[QuestionPoints]
,GoodAnswer = Case When TQ.[QuestionPoints] Is null Then 0
When TQ.[QuestionPoints] > 0 Then 1
Else 0 End
,WrongAnswer …Run Code Online (Sandbox Code Playgroud) 在另一个应用程序中,我被糟糕的设计震惊了:多个线程EnsureDatabaseSchemaExists()同时执行一个方法,它看起来基本上是这样的:
IF NOT EXISTS (SELECT * FROM sys.objects WHERE object_id = OBJECT_ID(N'MyTable') AND type = N'U') BEGIN
CREATE TABLE MyTable ( ... );
END
Run Code Online (Sandbox Code Playgroud)
但是,即使在 SERIALIZABLE 事务中执行,此代码似乎也不是线程安全的(即并行代码尝试多次创建表)。是否有机会强制 SELECT 语句获取阻止另一个线程执行相同 SELECT 语句的锁?
是否有更好的多线程 EnsureSchemaExists() 方法模式?
我一直在一个表中记录昂贵的运行查询及其查询计划,以便我们监控性能趋势并确定需要优化的区域。
然而,现在已经到了查询计划占用太多空间的地步(因为我们针对每个查询存储整个计划)。
因此,我试图通过将 QueryPlanHash 和 QueryPlan 提取到另一个表来规范化现有数据。
CREATE TABLE QueryPlans
(
QueryPlanHash VARBINARY(25),
QueryPlan XML,
CONSTRAINT PK_QueryPlans PRIMARY KEY
(
QueryPlanHash
)
);
Run Code Online (Sandbox Code Playgroud)
由于query_plan_hashin的定义sys.dm_exec_query_stats是一个二进制字段(并且我会定期插入新数据),因此我使用VARBINARY了新表中的数据类型。
但是,下面的插入失败了...
INSERT INTO QueryPlans
( QueryPlanHash, QueryPlan )
SELECT queryplanhash, queryplan
FROM
(
SELECT
p.value('(./@QueryPlanHash)[1]', 'varchar(20)') queryplanhash,
QueryPlan,
ROW_NUMBER() OVER (PARTITION BY p.value('(./@QueryPlanHash)[1]', 'varchar(20)') ORDER BY DateRecorded) rownum
FROM table
CROSS APPLY QueryPlan.nodes('/ShowPlanXML/BatchSequence/Batch/Statements/StmtSimple[@QueryPlanHash]') t(p)
) data
WHERE rownum = 1
Run Code Online (Sandbox Code Playgroud)
....有错误
Implicit conversion from data type varchar to varbinary is …Run Code Online (Sandbox Code Playgroud) 我最近继承了一个使用BINARY(16)而不是UNIQUEIDENTIFIER存储 Guid的 SQL Server 数据库。它对包括主键在内的所有内容都执行此操作。
我应该担心吗?
我有一段代码可以执行插入到高度非规范化的表中。这些表的列数从 ~100 到 300+ 不等。这是 SQL Server 2008 R2,在 Windows Server 2008 上运行。
每个插入包括插入到同一事务下的多个表。有些插入是由 NHibernate 批处理的,但有些不能,但它们都在同一个事务下。
当我通过重复调用一段执行插入的代码来执行插入 500 次时,我得到平均约 360 毫秒。
奇怪的是,当我使用 4 个进程(在 Windows Server 2008 下从 4 个不同的命令提示符运行相同的 exe)同时运行测试代码时,每次调用的插入性能变得更好。我看到突发速度高达 90 毫秒(快了几乎 X4)。我正在测量代码中的插入时间。
由于这 4 个进程彼此一无所知,我假设这与 SQL Server 有关,但我完全不知道为什么。我想知道为什么会发生这种情况,以及是否有任何配置可以让我在插入不那么频繁的情况下获得相同的性能。
同样欢迎有关 SQL Server 监视方法以了解数据库级别发生的情况的建议。
我varchar在 SQL Server 的表中有一个列,其中包含一个 base64 编码的文本字符串,我想将其解码为纯文本等效项
SQL Server 是否具有处理此类事情的任何本机功能?
一个示例 base64 字符串:
cm9sZToxIHByb2R1Y2VyOjEyIHRpbWVzdGFtcDoxNDY4NjQwMjIyNTcxMDAwIGxhdGxuZ3tsYXRpdHVkZV9lNzo0MTY5ODkzOTQgbG9uZ2l0dWRlX2U3Oi03Mzg5NjYyMTB9IHJhZGl1czoxOTc2NA==
Run Code Online (Sandbox Code Playgroud)
解码为:
role:1 producer:12 timestamp:1468640222571000 latlng{latitude_e7:416989394 longitude_e7:-738966210} radius:19764
Run Code Online (Sandbox Code Playgroud) sql-server t-sql sql-server-2008-r2 cast string-manipulation
sql-server ×10
cast ×1
foreign-key ×1
hardware ×1
join ×1
locking ×1
metadata ×1
migration ×1
optimization ×1
t-sql ×1
uuid ×1
varbinary ×1
varchar ×1
xml ×1