ಡೆಡ್‌ಲಾಕ್‌ಗಳು ಮತ್ತು ಲಾಕ್‌ಗಳಲ್ಲಿ ಡೆಸಿಫರ್ ಕೀ ಮತ್ತು ಪೇಜ್ ವೇಟ್‌ರಿಸೋರ್ಸ್

ನೀವು ನಿರ್ಬಂಧಿಸಲಾದ ಪ್ರಕ್ರಿಯೆ ವರದಿಯನ್ನು ಬಳಸಿದರೆ ಅಥವಾ SQL ಸರ್ವರ್ ಒದಗಿಸಿದ ಡೆಡ್‌ಲಾಕ್ ಗ್ರಾಫ್‌ಗಳನ್ನು ನಿಯತಕಾಲಿಕವಾಗಿ ಸಂಗ್ರಹಿಸಿದರೆ, ನೀವು ಈ ರೀತಿಯ ವಿಷಯಗಳನ್ನು ಎದುರಿಸುತ್ತೀರಿ:

waitresource="ಪುಟ: 6:3:70133"

waitresource=“KEY: 6:72057594041991168 (ce52f92a058c)“

ಕೆಲವೊಮ್ಮೆ, ನೀವು ಅಧ್ಯಯನ ಮಾಡುವ ದೈತ್ಯ XML ನಲ್ಲಿ ಹೆಚ್ಚಿನ ಮಾಹಿತಿ ಇರುತ್ತದೆ (ಡೆಡ್‌ಲಾಕ್ ಗ್ರಾಫ್‌ಗಳು ಆಬ್ಜೆಕ್ಟ್ ಮತ್ತು ಇಂಡೆಕ್ಸ್‌ನ ಹೆಸರುಗಳನ್ನು ಕಂಡುಹಿಡಿಯಲು ನಿಮಗೆ ಸಹಾಯ ಮಾಡುವ ಸಂಪನ್ಮೂಲಗಳ ಪಟ್ಟಿಯನ್ನು ಒಳಗೊಂಡಿರುತ್ತವೆ), ಆದರೆ ಯಾವಾಗಲೂ ಅಲ್ಲ.

ಈ ಪಠ್ಯವು ಅವುಗಳನ್ನು ಅರ್ಥಮಾಡಿಕೊಳ್ಳಲು ನಿಮಗೆ ಸಹಾಯ ಮಾಡುತ್ತದೆ.

ಇಲ್ಲಿರುವ ಎಲ್ಲಾ ಮಾಹಿತಿಯು ಅಂತರ್ಜಾಲದಲ್ಲಿ ವಿವಿಧ ಸ್ಥಳಗಳಲ್ಲಿದೆ, ಅದನ್ನು ಸರಳವಾಗಿ ವಿತರಿಸಲಾಗಿದೆ! DBCC PAGE ನಿಂದ hobt_id ವರೆಗೆ ದಾಖಲೆರಹಿತ %%physloc%% ಮತ್ತು %%lockres%% ಕಾರ್ಯಗಳವರೆಗೆ ಎಲ್ಲವನ್ನೂ ಒಟ್ಟಿಗೆ ಸೇರಿಸಲು ನಾನು ಬಯಸುತ್ತೇನೆ.

ಮೊದಲಿಗೆ, PAGE ಲಾಕ್‌ಗಳಲ್ಲಿ ಕಾಯುವಿಕೆಗಳ ಕುರಿತು ಮಾತನಾಡೋಣ, ತದನಂತರ KEY ಲಾಕ್‌ಗಳಿಗೆ ಹೋಗೋಣ.

1) waitresource="PAGE: 6:3:70133" = Database_Id: FileId: PageNumber

ನಿಮ್ಮ ವಿನಂತಿಯು PAGE ಲಾಕ್‌ನಲ್ಲಿ ಕಾಯುತ್ತಿದ್ದರೆ, SQL ಸರ್ವರ್ ನಿಮಗೆ ಆ ಪುಟದ ವಿಳಾಸವನ್ನು ನೀಡುತ್ತದೆ.

"ಪುಟ: 6:3:70133" ಅನ್ನು ಒಡೆಯುವುದರಿಂದ ನಾವು ಪಡೆಯುತ್ತೇವೆ:

  • ಡೇಟಾಬೇಸ್_ಐಡಿ = 6
  • data_file_id = 3
  • page_number = 70133

1.1) ಡೇಟಾಬೇಸ್_ಐಡಿ ಡೀಕ್ರಿಪ್ಟ್ ಮಾಡಿ

ಪ್ರಶ್ನೆಯನ್ನು ಬಳಸಿಕೊಂಡು ಡೇಟಾಬೇಸ್ ಹೆಸರನ್ನು ಹುಡುಕಿ:

SELECT 
    name 
FROM sys.databases 
WHERE database_id=6;
GO

ಇದು ಸಾರ್ವಜನಿಕವಾಗಿದೆ ಡಿಬಿ ವೈಡ್ ವರ್ಲ್ಡ್ ಆಮದುದಾರರು ನನ್ನ SQL ಸರ್ವರ್‌ನಲ್ಲಿ.

1.2) ಡೇಟಾ ಫೈಲ್‌ನ ಹೆಸರನ್ನು ಹುಡುಕಲಾಗುತ್ತಿದೆ - ನಿಮಗೆ ಆಸಕ್ತಿ ಇದ್ದರೆ

ಟೇಬಲ್ ಹೆಸರನ್ನು ಹುಡುಕಲು ನಾವು ಮುಂದಿನ ಹಂತದಲ್ಲಿ data_file_id ಅನ್ನು ಬಳಸಲಿದ್ದೇವೆ. ನೀವು ಮುಂದಿನ ಹಂತಕ್ಕೆ ಸ್ಕಿಪ್ ಮಾಡಬಹುದು, ಆದರೆ ನೀವು ಫೈಲ್ ಹೆಸರಿನಲ್ಲಿ ಆಸಕ್ತಿ ಹೊಂದಿದ್ದರೆ, ಕಂಡುಬರುವ ಡೇಟಾಬೇಸ್‌ನ ಸಂದರ್ಭದಲ್ಲಿ ಪ್ರಶ್ನೆಯನ್ನು ಚಲಾಯಿಸುವ ಮೂಲಕ ನೀವು ಅದನ್ನು ಕಂಡುಹಿಡಿಯಬಹುದು, ಈ ಪ್ರಶ್ನೆಗೆ data_file_id ಅನ್ನು ಬದಲಿಸಿ:

USE WideWorldImporters;
GO
SELECT 
    name, 
    physical_name
FROM sys.database_files
WHERE file_id = 3;
GO

ವೈಡ್‌ವರ್ಲ್ಡ್ ಆಮದುದಾರರ ಡೇಟಾಬೇಸ್‌ನಲ್ಲಿ ಇದು WWI_UserData ಎಂಬ ಫೈಲ್ ಆಗಿದೆ ಮತ್ತು ನಾನು ಅದನ್ನು C:MSSQLDATAWideWorldImporters_UserData.ndf ಗೆ ಮರುಸ್ಥಾಪಿಸಿದ್ದೇನೆ. (ಓಹ್, ಸಿಸ್ಟಮ್ ಡ್ರೈವ್‌ನಲ್ಲಿ ಫೈಲ್‌ಗಳನ್ನು ಹಾಕುವುದನ್ನು ನೀವು ಹಿಡಿದಿದ್ದೀರಿ! ಇಲ್ಲ! ಇದು ಮುಜುಗರದ ಸಂಗತಿ).

1.3) DBCC ಪುಟದಿಂದ ವಸ್ತುವಿನ ಹೆಸರನ್ನು ಪಡೆಯಿರಿ

ಡೇಟಾಫೈಲ್ 70133 ರಲ್ಲಿನ #3 ಪುಟವು ವರ್ಲ್ಡ್‌ವೈಡ್ ಆಮದುದಾರರ ಡೇಟಾಬೇಸ್‌ಗೆ ಸೇರಿದೆ ಎಂದು ನಮಗೆ ಈಗ ತಿಳಿದಿದೆ. ದಾಖಲೆರಹಿತ DBCC PAGE ಮತ್ತು ಟ್ರೇಸ್ ಫ್ಲ್ಯಾಗ್ 3604 ಅನ್ನು ಬಳಸಿಕೊಂಡು ನಾವು ಈ ಪುಟದ ವಿಷಯಗಳನ್ನು ನೋಡಬಹುದು.
ಗಮನಿಸಿ: ಬೇರೆ ಸರ್ವರ್‌ನಲ್ಲಿ ಎಲ್ಲೋ ಮರುಸ್ಥಾಪಿಸಿದ ನಕಲಿನಲ್ಲಿ DBCC ಪುಟವನ್ನು ಬಳಸಲು ನಾನು ಬಯಸುತ್ತೇನೆ, ಏಕೆಂದರೆ ಇದು ದಾಖಲೆರಹಿತ ವಿಷಯವಾಗಿದೆ. ಕೆಲವು ಸಂದರ್ಭಗಳಲ್ಲಿ, ಅವಳು ಡಂಪ್ಗೆ ಕಾರಣವಾಗಬಹುದು (ಅಂದಾಜು ಅನುವಾದಕ - ಲಿಂಕ್, ದುರದೃಷ್ಟವಶಾತ್, ಎಲ್ಲಿಯೂ ಮುನ್ನಡೆಸುವುದಿಲ್ಲ, ಆದರೆ url ಮೂಲಕ ನಿರ್ಣಯಿಸುವುದು, ನಾವು ಫಿಲ್ಟರ್ ಮಾಡಿದ ಸೂಚಿಕೆಗಳ ಬಗ್ಗೆ ಮಾತನಾಡುತ್ತಿದ್ದೇವೆ).

/* This trace flag makes DBCC PAGE output go to our Messages tab
instead of the SQL Server Error Log file */
DBCC TRACEON (3604);
GO
/* DBCC PAGE (DatabaseName, FileNumber, PageNumber, DumpStyle)*/
DBCC PAGE ('WideWorldImporters',3,70133,2);
GO

ಫಲಿತಾಂಶಗಳಿಗೆ ಸ್ಕ್ರೋಲ್ ಮಾಡುವ ಮೂಲಕ, ನೀವು object_id ಮತ್ತು index_id ಅನ್ನು ಕಂಡುಹಿಡಿಯಬಹುದು.
ಡೆಡ್‌ಲಾಕ್‌ಗಳು ಮತ್ತು ಲಾಕ್‌ಗಳಲ್ಲಿ ಡೆಸಿಫರ್ ಕೀ ಮತ್ತು ಪೇಜ್ ವೇಟ್‌ರಿಸೋರ್ಸ್
ಬಹುತೇಕ ಮುಗಿದಿದೆ! ಈಗ ನೀವು ಪ್ರಶ್ನೆಯೊಂದಿಗೆ ಟೇಬಲ್ ಮತ್ತು ಇಂಡೆಕ್ಸ್ ಹೆಸರುಗಳನ್ನು ಕಾಣಬಹುದು:

USE WideWorldImporters;
GO
SELECT 
    sc.name as schema_name, 
    so.name as object_name, 
    si.name as index_name
FROM sys.objects as so 
JOIN sys.indexes as si on 
    so.object_id=si.object_id
JOIN sys.schemas AS sc on 
    so.schema_id=sc.schema_id
WHERE 
    so.object_id = 94623380
    and si.index_id = 1;
GO

ಮತ್ತು ಇಲ್ಲಿ ನಾವು ಲಾಕ್‌ನಲ್ಲಿನ ಕಾಯುವಿಕೆಯು Sales.OrderLines ಕೋಷ್ಟಕದ PK_Sales_OrderLines ಸೂಚ್ಯಂಕದಲ್ಲಿದೆ ಎಂದು ನೋಡುತ್ತೇವೆ.

ಗಮನಿಸಿ: SQL ಸರ್ವರ್ 2014 ಮತ್ತು ಮೇಲಿನವುಗಳಲ್ಲಿ, ದಾಖಲೆರಹಿತ DMO sys.dm_db_database_page_allocations ಅನ್ನು ಬಳಸಿಕೊಂಡು ವಸ್ತುವಿನ ಹೆಸರನ್ನು ಸಹ ಕಾಣಬಹುದು. ಆದರೆ ನೀವು ಡೇಟಾಬೇಸ್‌ನಲ್ಲಿ ಪ್ರತಿ ಪುಟವನ್ನು ಪ್ರಶ್ನಿಸಬೇಕು, ಅದು ದೊಡ್ಡ ಡೇಟಾಬೇಸ್‌ಗಳಿಗೆ ತುಂಬಾ ತಂಪಾಗಿಲ್ಲ, ಹಾಗಾಗಿ ನಾನು DBCC PAGE ಅನ್ನು ಬಳಸಿದ್ದೇನೆ.

1.4) ನಿರ್ಬಂಧಿಸಲಾದ ಪುಟದಲ್ಲಿನ ಡೇಟಾವನ್ನು ನೋಡಲು ಸಾಧ್ಯವೇ?

ನುವು, ಹೌದು. ಆದರೆ... ನಿಮಗೆ ಇದು ನಿಜವಾಗಿಯೂ ಅಗತ್ಯವಿದೆಯೇ?
ಸಣ್ಣ ಟೇಬಲ್‌ಗಳಲ್ಲಿಯೂ ಇದು ನಿಧಾನವಾಗಿರುತ್ತದೆ. ಆದರೆ ಇದು ಒಂದು ರೀತಿಯ ತಂಪಾಗಿದೆ, ಆದ್ದರಿಂದ ನೀವು ಇಲ್ಲಿಯವರೆಗೆ ಓದಿರುವುದರಿಂದ ... %% physloc%% ಬಗ್ಗೆ ಮಾತನಾಡೋಣ!

%%physloc%% ಪ್ರತಿ ನಮೂದುಗೆ ಭೌತಿಕ ID ಹಿಂತಿರುಗಿಸುವ ದಾಖಲೆಯಿಲ್ಲದ ಮ್ಯಾಜಿಕ್ ತುಣುಕು. ನೀವು ಬಳಸಬಹುದು SQL ಸರ್ವರ್ 2008 ಮತ್ತು ಹೆಚ್ಚಿನದರಲ್ಲಿ sys.fn_PhysLocFormatter ಜೊತೆಗೆ %%physloc%%.

Sales.OrderLines ನಲ್ಲಿ ಪುಟವನ್ನು ನಿರ್ಬಂಧಿಸಲು ನಾವು ಬಯಸಿದ್ದೇವೆ ಎಂದು ಈಗ ನಮಗೆ ತಿಳಿದಿದೆ, ಕೆಳಗಿನ ಪ್ರಶ್ನೆಯೊಂದಿಗೆ ಪುಟ #3 ರಲ್ಲಿ ಡೇಟಾ ಫೈಲ್ #70133 ನಲ್ಲಿ ಸಂಗ್ರಹವಾಗಿರುವ ಈ ಕೋಷ್ಟಕದಲ್ಲಿನ ಎಲ್ಲಾ ಡೇಟಾವನ್ನು ನಾವು ನೋಡಬಹುದು:

Use WideWorldImporters;
GO
SELECT 
    sys.fn_PhysLocFormatter (%%physloc%%),
    *
FROM Sales.OrderLines (NOLOCK)
WHERE sys.fn_PhysLocFormatter (%%physloc%%) like '(3:70133%'
GO

ನಾನು ಹೇಳಿದಂತೆ, ಇದು ಸಣ್ಣ ಟೇಬಲ್‌ಗಳಲ್ಲಿಯೂ ನಿಧಾನವಾಗಿರುತ್ತದೆ. ನಾನು ವಿನಂತಿಗೆ NOLOCK ಅನ್ನು ಸೇರಿಸಿದ್ದೇನೆ ಏಕೆಂದರೆ ಲಾಕ್ ಪತ್ತೆಯಾದ ಸಮಯದಲ್ಲಿ ನಾವು ನೋಡಲು ಬಯಸುವ ಡೇಟಾವು ಒಂದೇ ಆಗಿರುತ್ತದೆ ಎಂದು ನಮಗೆ ಇನ್ನೂ ಯಾವುದೇ ಗ್ಯಾರಂಟಿ ಇಲ್ಲ - ಆದ್ದರಿಂದ ನಾವು ಸುರಕ್ಷಿತವಾಗಿ ಕೊಳಕು ಓದುವಿಕೆಯನ್ನು ಮಾಡಬಹುದು.
ಆದರೆ, ಹುರ್ರೇ, ನಮ್ಮ ಪ್ರಶ್ನೆಯು ಹೋರಾಡಿದ 25 ಸಾಲುಗಳನ್ನು ಪ್ರಶ್ನೆಯು ನನಗೆ ಹಿಂದಿರುಗಿಸುತ್ತದೆ.
ಡೆಡ್‌ಲಾಕ್‌ಗಳು ಮತ್ತು ಲಾಕ್‌ಗಳಲ್ಲಿ ಡೆಸಿಫರ್ ಕೀ ಮತ್ತು ಪೇಜ್ ವೇಟ್‌ರಿಸೋರ್ಸ್
PAGE ಲಾಕ್‌ಗಳ ಬಗ್ಗೆ ಸಾಕು. ನಾವು ಕೀ ಲಾಕ್‌ಗಾಗಿ ಕಾಯುತ್ತಿದ್ದರೆ ಏನು?

2) waitresource="KEY: 6:72057594041991168 (ce52f92a058c)" = Database_Id, HOBT_Id (ನೀವು ನಿಜವಾಗಿಯೂ ಬಯಸಿದರೆ %%lockres%% ನೊಂದಿಗೆ ಡೀಕ್ರಿಪ್ಟ್ ಮಾಡಬಹುದಾದ ಮ್ಯಾಜಿಕ್ ಹ್ಯಾಶ್)

ನಿಮ್ಮ ಪ್ರಶ್ನೆಯು ಸೂಚ್ಯಂಕ ಪ್ರವೇಶವನ್ನು ಲಾಕ್ ಮಾಡಲು ಪ್ರಯತ್ನಿಸಿದರೆ ಮತ್ತು ಅದರದೇ ಆದ ಲಾಕ್ ಆಗಿದ್ದರೆ, ನೀವು ಸಂಪೂರ್ಣವಾಗಿ ವಿಭಿನ್ನ ರೀತಿಯ ವಿಳಾಸವನ್ನು ಪಡೆಯುತ್ತೀರಿ.
“6:72057594041991168 (ce52f92a058c)” ಅನ್ನು ಭಾಗಗಳಾಗಿ ವಿಭಜಿಸಿದರೆ, ನಾವು ಪಡೆಯುತ್ತೇವೆ:

  • ಡೇಟಾಬೇಸ್_ಐಡಿ = 6
  • hobt_id = 72057594041991168
  • ಮ್ಯಾಜಿಕ್ ಹ್ಯಾಶ್ = (ce52f92a058c)

2.1) ಡೇಟಾಬೇಸ್_ಐಡಿ ಡೀಕ್ರಿಪ್ಟ್ ಮಾಡಿ

ಇದು ಮೇಲಿನ ಉದಾಹರಣೆಯಂತೆಯೇ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತದೆ! ಪ್ರಶ್ನೆಯನ್ನು ಬಳಸಿಕೊಂಡು ನಾವು ಡೇಟಾಬೇಸ್ ಹೆಸರನ್ನು ಕಂಡುಕೊಳ್ಳುತ್ತೇವೆ:

SELECT 
    name 
FROM sys.databases 
WHERE database_id=6;
GO

ನನ್ನ ವಿಷಯದಲ್ಲಿ, ಇದು ಒಂದೇ ಡಿಬಿ ವೈಡ್ ವರ್ಲ್ಡ್ ಆಮದುದಾರರು.

2.2) hobt_id ಡೀಕ್ರಿಪ್ಟ್ ಮಾಡಿ

ಕಂಡುಬರುವ ಡೇಟಾಬೇಸ್‌ನ ಸಂದರ್ಭದಲ್ಲಿ, ನೀವು ಟೇಬಲ್ ಮತ್ತು ಇಂಡೆಕ್ಸ್‌ನ ಹೆಸರುಗಳನ್ನು ನಿರ್ಧರಿಸಲು ಸಹಾಯ ಮಾಡುವ ಒಂದೆರಡು ಸೇರ್ಪಡೆಗಳೊಂದಿಗೆ sys.partitions ಅನ್ನು ಪ್ರಶ್ನಿಸಬೇಕಾಗಿದೆ ...

USE WideWorldImporters;
GO
SELECT 
    sc.name as schema_name, 
    so.name as object_name, 
    si.name as index_name
FROM sys.partitions AS p
JOIN sys.objects as so on 
    p.object_id=so.object_id
JOIN sys.indexes as si on 
    p.index_id=si.index_id and 
    p.object_id=si.object_id
JOIN sys.schemas AS sc on 
    so.schema_id=sc.schema_id
WHERE hobt_id = 72057594041991168;
GO

ಅಪ್ಲಿಕೇಶನ್‌ನಲ್ಲಿ ವಿನಂತಿಯು ಕಾಯುತ್ತಿದೆ ಎಂದು ಅದು ನನಗೆ ಹೇಳುತ್ತದೆ. PK_Application_Countries ಸೂಚಿಯನ್ನು ಬಳಸಿಕೊಂಡು ದೇಶಗಳು ಲಾಕ್ ಆಗಿವೆ.

2.3) ಈಗ ಕೆಲವು %%lockres%% ಮ್ಯಾಜಿಕ್‌ಗಾಗಿ - ಯಾವ ಪ್ರವೇಶವನ್ನು ಲಾಕ್ ಮಾಡಲಾಗಿದೆ ಎಂಬುದನ್ನು ನೀವು ಕಂಡುಹಿಡಿಯಲು ಬಯಸಿದರೆ

ಯಾವ ಸಾಲಿನಲ್ಲಿ ಲಾಕ್ ಅಗತ್ಯವಿದೆ ಎಂದು ನಾನು ನಿಜವಾಗಿಯೂ ತಿಳಿದುಕೊಳ್ಳಲು ಬಯಸಿದರೆ, ಟೇಬಲ್ ಅನ್ನು ಪ್ರಶ್ನಿಸುವ ಮೂಲಕ ನಾನು ಕಂಡುಹಿಡಿಯಬಹುದು. ಮ್ಯಾಜಿಕ್ ಹ್ಯಾಶ್‌ಗೆ ಹೊಂದಿಕೆಯಾಗುವ ನಮೂದನ್ನು ಹುಡುಕಲು ನಾವು ದಾಖಲೆರಹಿತ %%lockres%% ಕಾರ್ಯವನ್ನು ಬಳಸಬಹುದು.
ಈ ಪ್ರಶ್ನೆಯು ಸಂಪೂರ್ಣ ಟೇಬಲ್ ಅನ್ನು ಸ್ಕ್ಯಾನ್ ಮಾಡುತ್ತದೆ ಎಂಬುದನ್ನು ಗಮನಿಸಿ ಮತ್ತು ದೊಡ್ಡ ಕೋಷ್ಟಕಗಳಲ್ಲಿ ಇದು ತಮಾಷೆಯಾಗಿಲ್ಲ:

SELECT
    *
FROM Application.Countries (NOLOCK)
WHERE %%lockres%% = '(ce52f92a058c)';
GO

ನಾನು NOLOCK ಅನ್ನು ಸೇರಿಸಿದ್ದೇನೆ (ಟ್ವಿಟರ್‌ನಲ್ಲಿ ಕ್ಲಾಸ್ ಆಸ್ಚೆನ್‌ಬ್ರೆನ್ನರ್ ಅವರ ಸಲಹೆಯ ಮೇರೆಗೆ) ಏಕೆಂದರೆ ಬೀಗಗಳು ಸಮಸ್ಯೆಯಾಗಿರಬಹುದು. ನಾವು ಈಗ ಏನಿದೆ ಎಂಬುದನ್ನು ನೋಡಲು ಬಯಸುತ್ತೇವೆ, ಮತ್ತು ವಹಿವಾಟು ಪ್ರಾರಂಭವಾದಾಗ ಏನಿತ್ತು ಅಲ್ಲ - ಡೇಟಾ ಸ್ಥಿರತೆ ನಮಗೆ ಮುಖ್ಯ ಎಂದು ನಾನು ಭಾವಿಸುವುದಿಲ್ಲ.
Voila, ನಾವು ಹೋರಾಡಿದ ದಾಖಲೆ!
ಡೆಡ್‌ಲಾಕ್‌ಗಳು ಮತ್ತು ಲಾಕ್‌ಗಳಲ್ಲಿ ಡೆಸಿಫರ್ ಕೀ ಮತ್ತು ಪೇಜ್ ವೇಟ್‌ರಿಸೋರ್ಸ್

ಮನ್ನಣೆಗಳು ಮತ್ತು ಹೆಚ್ಚಿನ ಓದುವಿಕೆ

ಇವುಗಳಲ್ಲಿ ಹೆಚ್ಚಿನದನ್ನು ಯಾರು ಮೊದಲು ವಿವರಿಸಿದ್ದಾರೆಂದು ನನಗೆ ನೆನಪಿಲ್ಲ, ಆದರೆ ನೀವು ಇಷ್ಟಪಡಬಹುದಾದ ಕಡಿಮೆ ದಾಖಲಿತ ವಿಷಯಗಳ ಕುರಿತು ಎರಡು ಪೋಸ್ಟ್‌ಗಳು ಇಲ್ಲಿವೆ:

ಮೂಲ: www.habr.com

ಕಾಮೆಂಟ್ ಅನ್ನು ಸೇರಿಸಿ