Mình muốn chia sẻ với các bạn một điều mà không phải ai cũng biết, đó là nội dung hầu hết các khoá học ở Stanford được đưa lên mạng miễn phí. Các lớp học thường có website để sinh viên tiện tìm thông tin, và website đó thường có đầy đủ thông tin về bài giảng, bài tập về nhà, sách giáo khoa., ai cũng có thể vào xem.
Để biết mã các lớp học, bạn có thể vào explorecourses.stanford.edu Đây là trang danh mục các lớp học ở Stanford. Bạn có thể điền từ khoá để tìm. Ví dụ, bạn muốn học các lớp data science thì điền từ khoá data science, nó sẽ hiện ra thông tin các lớp học về data science như mã lớp học, tên lớp học, người dạy, nội dung giới thiệu lớp học. Bạn cũng có thể tìm các lớp học theo nghành.
Đây là danh sách mã một số lớp học ở Stanford mà mình rất thích.
Lập trình cơ bản: CS106A, CS106B
Hệ thống: CS107, CS110
Probability: CS109
Algorithm: CS161, CS168 (lớp của thầy siêu dễ thương)
An ninh mạng: CS255
Network: CS155
Decision making under uncertainty (đưa ra quyết định khi không đủ thông tin): CS238 (mình quý ông thầy lớp này kinh khủng)
Cryptocurrency (bitcoin các thứ): CS251
Xử lý dữ liệu khổng lồ: CS246
Khoá dạy về machine learning cho computer vision thần thánh: CS231N
Khoá dạy về machine learning cho natural language processing: CS224N
Khoá phân tích mạng lưới (analysis of network): CS224W
Các ngành không phải khoa học máy tính thì thường ít có website cho người ngoài (họ sử dụng website nội bộ). Nhưng nếu bạn tìm được lớp nào hay ho qua trang explorecourses, hãy thử tìm qua mạng xem có website của lớp đó khônh nhé.
Hầu hết mọi người đều làm việc kém hiệu quả vì sự mất tập trung. Theo nghiên cứu, khi chúng ta đang tập trung làm một việc gì đó mà có một việc khác xen vào (Ví dụ như nghe điện thoại) thì cần ít nhất 15 phút để có thể lấy lại được sự tập trung vào công việc chính.
Sự tập trung sẽ bị ảnh hưởng bởi những công việc không liên quan, bởi sự mệt mỏi vì làm việc dài nhiều giờ, bởi kỷ luật bản thân…
Nếu cũng đang rơi vào tình trạng trên thì Học viện Agile sẽ giới thiệu đến các bạn một phương pháp giúp bạn quản lý thời gian, làm việc tập trung, sáng tạo và thậm chí không biết mệt – có thể quen thuộc với nhiều người nhưng không phải ai cũng biết. Đó chính là Phương pháp Pomodoro, hay còn được biết đến với tên gọi phương pháp “quả cà chua”, do Francesco Cirillo phát triển.
1. Phương pháp “quả cà chua” Pomodoro là gì?
Pomodoro (Đầy đủ theo tiếng Anh là Pomodoro Technique) là 1 phương pháp quản trị thời gian để nâng cao tối đa sự tập trung trong công việc được giới thiệu bởi Francesco Cirillo – CEO của 1 công ty phần mềm người Italia vào năm 1980. Trong tiếng Italia Pomodoro có nghĩa là quả cà chua – Lý do là Francesco Cirillo đã dùng 1 chiếc đồng hồ hình quả cà chua để theo dõi thời gian khi sáng tạo ra phương pháp này
2. Pomodoro ra đời như thế nào?
Năm 1980, khi còn là sinh viên, Francesco Cirillo – CEO của 1 công ty phần mềm người Italia đã nhận thấy sự tập trung của mình thường giảm mạnh sau 1 khoảng thời gian và khi đó ông rất khó để giải quyết các bài tập. Sau đó Francesco Cirillo đưa ra giải pháp nghỉ ngắn giữa các phiên làm việc vì làm việc 1 thời gian dài liên tục. Ông đưa ra cách thức làm việc (học tập) tập trung cao trong thời gian 25 phút sau đó nghỉ ngắn 5 phút và lại bắt đầu 1 phiên làm việc 25 phút mới. Mỗi phiên làm việc 25 phút này, Francesco Cirillo gọi là 1 Pomodoro.
3. Phương pháp Pomodoro này sẽ phù hợp với ai?
Phương pháp quả cà chua phù hợp với những nhà phát triển, thiết kế hay bất cứ ai đang làm việc trong lĩnh vực sáng tạo: người viết sách, biên tập viên, kỹ sư phần mềm, lập trình game, ứng dụng, copywriter, nhân viên nội dung, viết kịch bản, phóng sự, nhà báo…. Tuy nhiên, nói thế không có nghĩa là Pomodoro không thể được sử dụng bởi những người làm việc trong lĩnh vực khác. Bất cứ ai đang bị “bội thực” hay có một đống công việc đang cần được giải quyết và cảm thấy bất lực vì không thể tập trung dù chỉ trong một thời gian ngắn thì “quả cà chua” đều phát huy tác dụng. Có một câu chuyện như thế này! Chuyện kể rằng có chàng trai to khỏe nghe tin bà chủ khu rừng nọ tuyển thợ cưa. Anh tới ứng tuyển thì thấy “đối thủ” của mình là một bác nhìn như người lùn. Tới ngày thi, bà chủ đưa cho mỗi người một cái cưa và hai người sẽ ở hai mảnh rừng khác nhau để thử thách. Chàng trai tin chắc phần thắng trong tay mình và hì hục cưa ngày cưa đêm không ngừng nghỉ. Điều làm chàng băn khoăn nhất là rất nhiều lúc trong ngày, thấy bác thợ lùn vác cưa đi ngang qua với tách trà nóng hổi, vừa đi vừa huýt sáo và lúc nào cũng tươi cười. Chàng nghĩ bụng: “Đã già, lùn, lại còn… lười. Ta mặc kệ, phần thắng ắt hẳn về ta”. Hết thời gian, bà chủ tới nghiệm thu và thông báo kết quả. Bác lùn kia được chọn. Chàng trai bực lắm và quyết hỏi bà chủ cho ra nhẽ. Bà chủ đáp rằng: “Bác kia cưa được gỗ nhiều gấp rưỡi anh!” Chàng trai suy nghĩ mãi vẫn không thể lý giải nổi vì sao “người đàn ông vừa lùn vừa lười” kia lại có thể thắng mình nên đã quyết định tới hỏi chuyện. “Này, bác ăn trộm gỗ của tôi hả? Bác lười thế sao mà nhiều gỗ hơn tôi được?” Bác lùn cười lớn rồi giải thích rằng khi chàng ta cưa hì hục như thế mà không nghỉ, lưỡi cưa sẽ ngày càng cùn, hiệu suất sẽ ngày càng giảm. Còn bác cứ cưa khoảng một tiếng, lại xách cưa ra bờ suối ngồi mài, nhờ đó mà lưỡi cưa luôn sắc bén, giúp bác cưa nhanh hơn mà không mất quá nhiều sức.
4. Phương pháp Pomodoro được thực hiện như thế nào?
Có sáu bước trong quy trình thực hiện phương pháp này: Quyết định về nhiệm vụ phải làm (bạn nên có độ ưu tiên công việc nào phải thực hiện trước) Đặt bộ hẹn giờ Pomodoro (thông thường là 25 phút). Làm việc tập trung hoàn toàn cho đến khi hết 25p và không được gián đoạn. Kết thúc công việc khi bộ hẹn giờ đổ chuông và đánh dấu trên một miếng giấy. Nghỉ ngơi 3-5 phút sau mỗi Pomodoro Sau khi thực hiện được 4 pomodoro, bạn hãy nghỉ ngơi lâu hơn (15-30 phút), sau đó đặt lại bộ hẹn giờ thành 0, sau đó làm lại từ bước 1.
5. Nguyên tắc khi thực hiện phương pháp Pomodoro
Trong 1 Pomodoro (quy trình làm 25 phút, nghỉ 5 phút), nếu bạn buộc phải gián đoạn thì Pomodoro sẽ được tính lại từ đầu, không có 1/2 hay 2/3 Pomodoro. Chỉ tập trung làm 1 việc duy nhất với 100% thời gian đã định. Nếu công việc xong trước khi Pomodoro kết thúc, bạn cần dùng thời gian còn lại để kiểm tra và tối ưu hóa công việc cho đến hết Pomodoro đó. Trong các khoảng thời gian nghỉ (nghỉ 5 phút, 10 phút), bạn cần phải nghỉ ngơi thực sự. Hãy nhắm mắt thư giãn, nghe nhạc, uống nước, mát xa đầu, khuôn mặt, thiền, sắp xếp bàn làm việc, đi dạo trong văn phòng hoặc làm những việc đơn giản không cần sử dụng tư duy nhiều. Khi nghỉ, tuyệt đối tránh mọi thứ liên quan tới Internet, Facebook… vì chúng có thể sẽ kích thích sự hưng phấn của bạn, song bản chất vẫn làm bộ não thêm mệt mỏi. Bạn có thể tham khảo về phương pháp Pomodoro qua video dưới đây: https://www.youtube.com/watch?v=wUG_XpLF8sg
6. Các ứng dụng hỗ trợ tối ưu hóa phương pháp Pomodoro trong công việc
a. Truy cập vào trang web http://tomato-timer.com/ để có một chiếc đồng hồ điện tử giúp theo dõi Pomodoro. Để bắt đầu, bạn chỉ việc nhấn chọn Start. 25 phút sẽ bắt đầu trôi qua và đây là thời gian mà bạn sẽ phải tập trung hết cỡ với công việc hiện tại của mình. Sau khi hết 25 phút, nhấn tổ hợp Alt + S để thưởng cho mình 5 phút nghỉ giải lao. Khi hết 5 phút, một khoảng thời gian 25 phút mới lại bắt đầu. Cứ 4 lần nghỉ giao lao 5 phút như vậy thì bạn sẽ được nghỉ lâu hơn với 10 phút bằng cách nhấn Alt + L. Bạn có thể lặp đi lặp lại vòng tuần hoàn này trong 8 tiếng làm việc tại văn phòng và bạn sẽ thấy mình làm được nhiều việc hơn nhưng lại không hề cảm thấy chán hay mệt mỏi như trước nữa.
b. Marinara Timer là ứng dụng web cho phép bạn thiết lập thời gian nghỉ giải lao và làm việc. Nhìn chung, cách sử dụng khá giống với Tomato Timer.
c. Tomighty (Win/Mac/Linux) là phần mềm đa nền tảng cho phép bạn cài đặt trên máy tính để có thể sử dụng thuận lợi hơn.
d. Pomodorable (OS X) là sự kết hợp giữa một phần mềm quản lý thời gian theo phương pháp Pomodoro và một phần mềm todo list. Với Pomodorable, bạn sẽ nắm được khi nào các công việc hoàn thành, việc gì cần làm tiếp theo và cần thiết lập bao nhiêu Pomodoro để làm xong một đầu việc.
e. Simple Pomodoro (Android) là ứng dụng theo dõi thời gian không có nhiều tùy chỉnh như các công cụ khác. Tuy nhiên, nó cũng cung cấp cho bạn các thông báo hữu ích khi đến giờ nghỉ ngơi, làm việc và nắm được bao nhiêu Pomodoro bạn đã hoàn thành trong ngày. Quan trọng hơn, SimplePomodoro cũng tương thích với Google Tasks.
f. Focus Timer (iOS) rất lý tưởng cho iPhone và iPad. Bạn có thể tùy biến khoảng thời gian theo ý thích, âm thanh thông báo, xem lại lịch sử làm việc và ứng dụng này cũng cung cấp một hệ thống đánh giá dựa trên ngôi sao để tạo động lực cố gắng cho bạn.
Cuối cùng, điều quan trọng cần nhớ là Pomodoro là một phương pháp tối ưu hóa năng suất làm việc, hướng đến khả năng tăng sự tập trung, tránh mệt mỏi chứ không hẳn sẽ giúp bạn quản lý thời gian. Do vậy, bạn có thể kết hợp với các kỹ thuật khác như phương pháp Ma trận Eisenhower để có thể kiểm soát tốt hơn mọi thứ trong cuộc sống.
Một điều chắc chắn là khi mới bắt đầu, bạn sẽ gặp khá nhiều khó khăn, chẳng hạn như phải mất đến 5 hoặc 6 Pomodoro thì mới có thể làm xong một công việc hay chưa tập trung hoàn toàn. Bởi lẽ, Pomodoro đòi hỏi sự nỗ lực từ bản thân mỗi người rất cao và chỉ thực sự tác động tới cách bạn làm việc khi có cố gắng .Tuy nhiên, nếu kiên trì áp dụng, bạn chắc chắn sẽ nhận được kết quả.
Thông qua bài viết này mình sẽ hướng dẫn các bạn làm quen và hiểu thêm về công nghệ Blockchain.
Mục đích
– Tạo hệ thống Blockchain đơn giản nhất.
– Tạo hệ thống mining (poor of work) đơn giản.
– Khám phá thêm về Blockchain.
Kiến thức cần chuẩn bị: OOP, biết 1 ngôn ngữ hướng đội tượng.
Ok giờ xắn tay vào việc nào
Making the Blockchain.
Một blockchain là danh sách, chuỗi các khối (A blockchain is just a chain/list of blocks). Mỗi block trong blockchain sẽ chứa chữ ký số của nó, chữ ký số của khối trước nó và dữ liệu của khối (dữ liệu giao dịch là một ví dụ).
Hash = Digital Signature.
Mỗi khối không chỉ chứa mã hash của khối trước nó mà nó còn chứa mã hash của chính nó, được tính toán dựa trên mã hash của khối trước nó. Nếu dữ liệu khối trước đó bị thay đổi (khối A), việc này dẫn tới thay đổi mã hash của khối A, do mã hash được tính toán dựa trên data này. Việc này dẫn tới sự thay đổi mã hash của tất cả các khối trong chuỗi. Việc tính toán và so sánh giúp chúng ta phát hiện ra bất kì sự thay đổi nào trong blockchain.
Điều này có nghĩa là gì? – Nghĩa là khi thay đổi dữ liệu của 1 block thì sẽ dẫn tới thay đổi dữ liệu của rất rất nhiều block, và dãn tới thay đổi chain (break the chain).
Giờ chúng ta sẽ thừ bắt đầu xây dựng một hệ thống Blockchain đơn giản.
Tạo project đặt tên là NoobChain
Thêm class Block để xây dựng blockchain
class Block
{
public String hash;
public String previousHash;
private String data; // Trong ví dụ này chúng ta chỉ lưu data là một thông báo.
private long timeStamp;
//Block Constructor.
public Block(String data, String previousHash)
{
this.data = data;
this.previousHash = previousHash;
this.timeStamp = DatetimeHandle.GetTime();
}
}
Như bạn thấy Block cơ bản của chúng ta chứa một chuỗi hash sẽ dùng để lưu chữ kí số. Một biến previousHash để lưu hash của khối trước nó, và dữ liệu của khối.
Bước tiếp theo chúng ta sẽ tiến hành tạo chữ ký số.
Tạo lớp HashSha256, áp dụng thuật toán sha256 để sinh chuỗi, với nội dung như sau:
class HashSha256
{
public override string Hash(string strInput)
{
try
{
var crypt = new System.Security.Cryptography.SHA256Managed();
var hash = new System.Text.StringBuilder();
byte[] crypto = crypt.ComputeHash(Encoding.UTF8.GetBytes(strInput));
foreach (byte theByte in crypto)
{
hash.Append(theByte.ToString("x2"));
}
return hash.ToString();
}
catch (Exception e)
{
throw e;
}
}
}
Sau đó quay trờ lại lớp Block thêm và hàm tính mã hash
public String CalculateHash()
{
HashSha256 sha256 = new HashSha256();
String calculatedhash = sha256.Hash(
previousHash +
timeStamp.ToString()
data);
return calculatedhash;
}
.. và thêm hàm này vào contructor của lớp Block
public Block(String data, String previousHash)
{
this.data = data;
this.previousHash = previousHash;
this.timeStamp = DatetimeHandle.GetTime();
this.hash = CalculateHash(); // thêm hàm này vào cuối để chắc chắn các dữ liệu khác được init trước khi gọi hàm
}
Ok, giờ chúng ta thử kiểm tra lại công việc vừa làm xem…
Trong hàm Main của class program.cs chúng ta sẽ viết đoạn code để hiển thị chuỗi hash
Khối đầu tiên được gọi là genesis block, và vì nó không có khối phía trước nên ta sẽ gán previousHash của nó bằng 0
class Program
{
static void Main(string[] args)
{
Block genesisBlock = new Block("Hi im the first block", "0");
Console.WriteLine("Hash for block 1 : " + genesisBlock.hash);
Block secondBlock = new Block("Yo im the second block", genesisBlock.hash);
Console.WriteLine("Hash for block 2 : " + secondBlock.hash);
Block thirdBlock = new Block("Hey im the third block", secondBlock.hash);
Console.WriteLine("Hash for block 3 : " + thirdBlock.hash);
Console.ReadLine();
}
}
Output của chúng ta sẽ là 3 mã hash
Mỗi block giờ sẽ chứa chữ kí số được xây dựng trên thông tin của nó và chữ ký số của khối phía trước.
Để giống với khái niệm blockchain hơn, ta sẽ lưu trữ các block này trong List
Chỉnh sửa file program.cs như sau:
class Program
{
public static List<Block> blockchain = new List<Block>();
static void Main(string[] args)
{
blockchain.add(new Block("Hi im the first block", "0"));
blockchain.add(new Block("Yo im the second block",blockchain.ElementAt(blockchain.size()-1).hash));
blockchain.add(new Block("Hey im the third block",blockchain.ElementAt(blockchain.size()-1).hash));
string printBlockChain = new System.Web.Script.Serialization.JavaScriptSerializer().Serialize(blockchain);
Console.WriteLine(printBlockChain);
Console.ReadLine();
}
}
Để sử dụng được JavaScriptSerializer thì các bạn làm như sau
Right click References and do Add Reference, then from Assemblies->Framework select System.Web.Extensions
Chạy lại ứng dụng và xem kết quả thử nhé mọi người
Kiểm tra tính toàn vẹn của blockchain.
Chúng ta sẽ viết phương thức IsChainValid() kiểu boolean trong file program.cs. Phương thức nãy sẽ loop qua tất cả các block trong chain và so sánh các chuỗi hash. Phương thức này sẽ cần kiểm tra biến hash so sánh nó với chuỗi hash được tính toán, và chỗi hash ở khối trước so sánh với biến previousHash. Uhm, nghe có vẻ phức tạp, thử nhìn code xem có dễ hiểu hơn không nào.
public static Boolean IsChainValid()
{
Block currentBlock;
Block previousBlock;
//loop through blockchain to check hashes:
for (int i = 1; i < blockchain.Count; i++)
{
currentBlock = blockchain.ElementAt(i);
previousBlock = blockchain.ElementAt(i - 1);
//compare registered hash and calculated hash:
if (!currentBlock.hash.Equals(currentBlock.CalculateHash()))
{
Console.WriteLine("Current Hashes not equal");
return false;
}
//compare previous hash and registered previous hash
if (!previousBlock.hash.Equals(currentBlock.previousHash))
{
Console.WriteLine("Previous Hashes not equal");
return false;
}
}
return true;
}
Bất kì một thay đổi nào với mỗi block phương thức này sẽ trả về false.
Trên mạng lưới bitcoin, các nodes chia sẻ các blockchain và chuỗi hợp lệ dài nhất sẽ được châp nhận bởi hệ thống. Vậy nếu một hacker giả mạo một khối và tạo nên chuỗi blockchain mới cho mạng thì sao. Điều này là bất khả thi, vì sao? Giả sử hacker có thể xâm nhập và thay đổi một khối dữ liệu, điều này dẫn tới các dữ liệu tiếp theo của khối này cũng bị thay đổi. Vì vậy cần rất nhiều thời gian và sức mạnh tính toán để hacker có thể vượt hơn được so với sức mạnh tính toán của các thành viên còn lại trong hệ thống khi kết hợp.
Đào tiền ảo, cày sâu hay lướt sóng?
Lets start mining blocks!!!
Chúng ta sẽ yêu cầu minner tiến hành đào-coin bằng cách bắt họ phải thử các biến khác nhau trong block cho đến khi chuỗi hash bắt đầu với giá trị 0. Tại sao lại là 0?. Bạn có thể quy ước là bất cứ giá trị gì, tùy thuộc vào genesis hash của bạn. Trong trường hợp này chúng ta chọn 0.
Tiếp theo chúng ta thêm biến nonce trong hàm CalculateHash(), và thêm hàm MineBlock() như sau:
class Block
{
public String hash;
public String previousHash;
private String data; //our data will be a simple message.
private long timeStamp; //as number of milliseconds since 1/1/1970.
private int nonce = 0;
//Block Constructor.
public Block(String data, String previousHash)
{
this.data = data;
this.previousHash = previousHash;
this.timeStamp = DatetimeHandle.GetTime();
this.hash = CalculateHash();
}
public String CalculateHash()
{
HashSha256 sha256 = new HashSha256();
String calculatedhash = sha256.Hash(
previousHash +
timeStamp.ToString() +
nonce.ToString() +
data);
return calculatedhash;
}
public void MineBlock(int difficulty)
{
var str = new String(new char[difficulty]);
String target = new String(new char[difficulty]).Replace('\0', '0'); //Create a string with difficulty * "0"
while (!hash.Substring(0, difficulty).Equals(target))
{
nonce++;
hash = CalculateHash();
}
Console.WriteLine("Block Mined!!! : " + hash);
}
}
Phương thức MineBlock() truyền vào tham số difficulty kiểu int để quy định độ khó của thuật toán. Các bạn có thể thay đổi tham số này để kiểm tra tốc độ đào-coin khi chạy chương trình. Ở ví dụ này mình khuyến khích các bạn đặt ở mức 4-6 cho việc testing. Ex, Hiện tại độ khó của Litecoin là khoảng 442,592, khá kinh khủng.
Chúng ta thêm biến difficulty vào lớp program.cs:
public static int difficulty = 5;
Tiếp đó chúng ta cập nhật lớp program.cs, gọi hàm MineBlock() cho mỗi block mới. Phương thức IsChainValid() cũng được gọi sau khi đào được coin :D.
class Program
{
public static List<Block> blockchain = new List<Block>();
public static int difficulty = 5;
static void Main(string[] args)
{
blockchain.Add(new Block("Hi im the first block", "0"));
Console.WriteLine("Trying to Mine block 1... ");
blockchain.ElementAt(0).MineBlock(difficulty);
blockchain.Add(new Block("Yo im the second block", blockchain.ElementAt(blockchain.Count - 1).hash));
Console.WriteLine("Trying to Mine block 2... ");
blockchain.ElementAt(blockchain.Count - 1).MineBlock(difficulty);
blockchain.Add(new Block("Hey im the third block", blockchain.ElementAt(blockchain.Count - 1).hash));
Console.WriteLine("Trying to Mine block 3... ");
blockchain.ElementAt(blockchain.Count - 1).MineBlock(difficulty);
Console.WriteLine("\nBlockchain is Valid: " + IsChainValid());
string printBlockChain = new System.Web.Script.Serialization.JavaScriptSerializer().Serialize(blockchain);
Console.WriteLine(printBlockChain);
Console.ReadLine();
}
public static Boolean IsChainValid()
{
Block currentBlock;
Block previousBlock;
//loop through blockchain to check hashes:
for (int i = 1; i < blockchain.Count; i++)
{
currentBlock = blockchain.ElementAt(i);
previousBlock = blockchain.ElementAt(i - 1);
//compare registered hash and calculated hash:
if (!currentBlock.hash.Equals(currentBlock.CalculateHash()))
{
Console.WriteLine("Current Hashes not equal");
return false;
}
//compare previous hash and registered previous hash
if (!previousBlock.hash.Equals(currentBlock.previousHash))
{
Console.WriteLine("Previous Hashes not equal");
return false;
}
}
return true;
}
}
Chạy thử và xem kết quả nhé
Ối zồi ôi tôi đào được coin rồi này
Kết
Một blockchain giả mạo sẽ không thể bắt kịp chuỗi dài hơn và hợp lệ trừ khi chúng có tốc độ tính toán lớn hơn tất cả các nút khác trong mạng của bạn kết hợp. Một máy tính lượng tử trong tương lai hay gì đó (người ngoài hành tinh?)
Trong dự án asp net core, khi các bạn sử dụng Generic Repository Pattern, làm cách nào để register generic interface và implementation generic interface bằng cách sử dụng ASP.NET Core DI container?
Ok, với một interface đơn giản và implementation của nó, ta sử dụng như sau
Chúng ta cùng xem lại phát biểu về phương thức AddSingleton
public static IServiceCollection AddSingleton<TService, TImplementation>(this IServiceCollection serviceswhere TService : class where TImplementation : class, Tservice
Phương pháp này sử dụng được với hầu hết các trường hợp, ngoại trừ các service generic..
Xét một ví dụ đơn giản, chúng ta có interface
public interface IThing<T>
{
string GetName { get; }
}
và một implementation của nó như sau
public class GenericThing<T> : IThing<T>
{
public GenericThing()
{
GetName = typeof(T).Name;
}
public string GetName { get; }
}
Câu hỏi đặt ra là khi sử dụng IThing<SomeType> làm sao chúng ta lấy được chính xác GenericThing<SomeType> đã được injected vào?
Trong trường hợp này chúng ta sử dụng phương thức mở rộng khác trong ServiceCollection, bằng cách như sau