He creado una tabla SQL muy básica de la siguiente manera
CREATE TABLE [dbo].[TickData](
[Date] [varchar](12) NULL,
[Time] [varchar](12) NOT NULL,
[Symbol] [varchar](12) NOT NULL,
[Side] [varchar](2) NOT NULL,
[Depth] [varchar](2) NOT NULL,
[Quote] [varchar](12) NOT NULL,
[Size] [varchar](18) NOT NULL
) ON [PRIMARY]
Luego realicé una inserción a granel de 3 conciertos
BULK
INSERT TickData
FROM
'C:\SUMO.csv'
GO
Luego, el uso de RAM para el servidor SQL se disparó, consumiendo ~ 30Go de RAM:
Prefiero pensar que este es un comportamiento anormal y que se pueden tomar medidas para evitarlo.
EDITAR:
Ok, este parece ser el comportamiento predeterminado. Lo suficientemente justo.
Sin embargo, ¿por qué no se libera memoria mucho después de que finaliza la inserción masiva?
Un par de consideraciones adicionales:
A partir de los comentarios sobre el servidor SQL que libera la memoria cuando el sistema operativo "lo indica", mi experiencia práctica en un servidor Xeon de 32 Gb y 24 núcleos demuestra que esto es inexacto: una vez que finaliza un extracto BCP con memoria de gran volumen Tengo un grupo de instancias .Net de mi aplicación de procesamiento de datos que necesitan procesar los datos extraídos, y se quedan atorados / peleando para compartir la memoria restante para intentar realizar sus trabajos, lo que lleva mucho más tiempo que cuando se activa SQL Server apagado y la memoria está disponible para todas las aplicaciones para compartir. Tengo que detener el Agente SQL Server para que todo funcione sin problemas y evitar que las aplicaciones se bloqueen porque Articiallt causó la excepción OutOfMemmroy. En cuanto a la limitación / limitación artificial de la memoria brutal, si hay disponible memoria libre, ¿Por qué no usarlo? Idealmente, preferiría establecerse dinámicamente para adaptarse a lo que está disponible en lugar de limitarse forzosamente "al azar". Pero supongo que esto es por diseño, por lo que el caso se cerró en este último punto.
fuente
Respuestas:
Es un comportamiento normal para SQL Server asignar tanta memoria como sea posible a su grupo de búferes. Las bases de datos funcionan mejor con mucho buffer. Si desea cambiar el comportamiento, puede establecer la configuración de 'memoria máxima del servidor' . Una buena lectura de fondo sobre eso está aquí.
fuente
Si realmente desea que el sistema operativo recupere la memoria de SQL Server, tome un gran archivo de 20 GB y cópielo a través de la red. SQL Server liberará la memoria cuando el sistema operativo la necesite. Pero vería una variedad de contadores de rendimiento mientras esto sucede, y vería cómo cambia el rendimiento de su BULK INSERT si lo vuelve a ejecutar mientras se ejecuta la copia o inmediatamente después.
Si desea hacer esto manualmente, debe establecer un límite inferior en la configuración de memoria máxima del servidor SQL Server y reiniciar el servicio. Ahora SQL Server no usará 28GB incluso si lo necesita. Pero esto parece limitar artificialmente SQL Server.
Lo que parece esperar es un comportamiento más flexible, donde puede tener memoria libre parte del tiempo. ¿Con qué propósito? ¿Es esto como reducir un archivo de base de datos para liberar espacio en disco que no puede usar para otros fines porque el archivo de base de datos volverá a crecer?
Es curioso, si escribe una búsqueda en Google de "por qué SQL Server no", el autocompletado más común es "liberar memoria".
fuente
Desafortunadamente, esto es por diseño, por favor consulte esta publicación. Sin embargo, en esta publicación le da algunas instrucciones sobre cómo controlarlo.
/server/251832/sql-server-bulk-insert-physical-memory-issue
Asignación de memoria Editar
La memoria no está
freed
activa porque asigna memoria de manera muy similar a una aplicación .NET. Dado que la asignación de memoria es costosa, mantendrá esa asignación a menos que el SO lo solicite. Pero, no temas, si el sistema operativo quiere la memoria, la obtendrá, tal como lo hace en una aplicación .NET.fuente