Welcome to the next stage of our AI journey!
So far, we've learned how LLMs work, tokens, temperature, Top-P, Top-K, roles, context, and memory.
Now we're going to learn a skill you can use immediately: Prompt Engineering.
Prompt engineering means designing and improving the instructions you give an AI model so that it produces more useful, relevant, and appropriately formatted results.
Think of an LLM as a capable assistant. Your prompt is the task description you give that assistant. A vague task description often leads to a vague answer, while a clear one gives the model better guidance.
Imagine you want an AI to help you learn C#.
The goal isn't to make every prompt long. The goal is to provide the information that matters for the task.
Zero-shot prompting
One-shot prompting
Few-shot prompting
Many-shot prompting
The main difference is how many examples you provide to guide the model.
The boundaries between "few" and "many" aren't fixed technical standards. The important distinction is the number and usefulness of the examples.
Zero-shot prompting means asking the model to perform a task without providing input-output examples in the prompt.
The model uses its existing learned capabilities and your instructions to generate an answer.
When should you use zero-shot?
Summarizing a document.
Translating text.
Explaining a technical concept.
Extracting a clearly specified field.
Classifying straightforward examples when the categories are well defined.
Zero-shot prompting is usually the first technique to try because it is simple and economical.
One-shot prompting provides one example so that the model can infer the expected pattern.
One example does not guarantee that the model will generalize correctly. The example should be representative, and ambiguous business definitions should be stated explicitly.
Few-shot prompting provides multiple examples to help the model recognize a pattern.
This is especially useful when the task depends on business-specific rules.
Many-shot prompting provides a substantially larger number of examples in the prompt.
For example, you might include dozens or hundreds of verified material descriptions and their corresponding categories.
This may help when:
The task has many variations.
Examples communicate subtle distinctions more clearly than a short instruction.
The model needs to follow a specialized output convention.
But more examples do not automatically mean better results. Duplicated, inconsistent, or incorrect examples can confuse the model. Large prompts also consume context and can increase cost and latency.
For very large knowledge collections, retrieving the most relevant examples dynamically can be more efficient than including every example in every request.
A practical workflow is to start with zero-shot, evaluate the results, and add examples only when they address a real failure.
Chain-of-Thought prompting is a technique intended to encourage a model to work through intermediate reasoning steps on tasks that require multiple steps
A simple prompt asks for the answer. A reasoning-oriented prompt asks the model to break the problem into steps.
Important distinction: asking for a concise explanation is not the same as requiring a model to reveal its full internal reasoning. For practical applications, request a clear answer, verifiable calculations, and a brief rationale appropriate to the task.
CoT-style prompting can help on some multi-step tasks, but it is not guaranteed to improve every model or problem. Always validate the result.
These techniques combine the idea of reasoning-oriented prompts with the number of examples supplied.
The difference is straightforward:
Zero-shot CoT: ask for step-by-step problem solving without worked examples.
Few-shot CoT: demonstrate the desired solution pattern with examples.
Few-shot CoT can be useful when you need consistent intermediate calculations or a specific explanation format. Ensure the examples themselves are correct.
You also listed triple quotes, tags, and headings. These techniques help separate instructions, input data, and expected output.
Triple quotes can make a block of text easier to distinguish from the instructions surrounding it.
Summarize the following incident report in three bullet points.
"""
The inventory service returned duplicate material records.
The issue occurred after a database view was modified.
The team identified a join that multiplied rows.
"""
The triple quotes are ordinary text delimiters in this example. They are not magical tokens that guarantee better answers.
Tags can clearly identify different parts of a prompt.
<role>
You are a senior SQL developer.
</role>
<task>
Identify possible causes of duplicate rows.
</task>
<context>
The query joins Inventory and Material.
</context>
<format>
Return likely causes and suggested SQL checks.
</format>
Tags such as these are user-designed labels. They can improve clarity, but they don't automatically create special model roles or enforce security rules.
Markdown headings organize longer prompts into sections.
# Role
Act as a senior .NET architect.
## Task
Review the following API design.
## Constraints
- Follow SOLID principles.
- Identify security risks.
- Avoid unnecessary complexity.
## Output
1. Findings
2. Recommendations
3. Example implementation
Use headings for readability, tags for clearly labeled sections, and delimiters to distinguish supplied content from instructions.
These techniques can be combined. Choose the format that makes the prompt easiest to understand and maintain.
Let's build a production-oriented prompt using your selected options: Senior .NET architect + Few-shot prompting + Short bullet-point summary, following SOLID principles and avoiding unnecessary complexity.
The key idea is to give the AI a clear role, a precise review task, a few examples of the expected findings, and a concise output format.
You are a senior .NET architect with 15+ years of experience in C#, ASP.NET Core Web API, Entity Framework Core, SQL Server, and Clean Architecture.
Review the C# API method provided below. Identify meaningful bugs, performance problems, security risks, maintainability issues, and violations of SOLID principles.
Focus on actionable improvements rather than cosmetic changes.
The code belongs to a production ASP.NET Core Web API application. The application uses dependency injection, Entity Framework Core, and SQL Server.
Assume that the method should be maintainable, testable, secure, and efficient.
Follow SOLID principles and Clean Architecture where applicable.
Avoid unnecessary abstraction, overengineering, and premature optimization.
Preserve existing business behavior unless a defect requires a change.
Do not invent requirements or assume facts that are not evident from the code.
Distinguish confirmed defects from potential risks.
Do not flag a design choice as a defect without explaining its practical impact.
Recommend asynchronous database operations when appropriate.
Consider input validation, authorization, exception handling, cancellation tokens, and database query efficiency where relevant.
If additional context is required, state the assumption or ask a focused question.
Do not rewrite the entire method unless requested.
Input:
public async Task<List<Product>> GetProductsAsync()
{
var products = await _dbContext.Products.ToListAsync();
return products
.Where(p => p.IsActive)
.ToList();
}
Expected output:
Issue — Performance: All products are loaded into application memory before filtering.
Recommendation: Apply Where(p => p.IsActive) before ToListAsync() so SQL Server filters the records.
Priority: Medium; impact depends on table size and query usage.
Input:
public class OrderService
{
public decimal CalculateTotal(Order order)
{
// Calculate total and save the order to SQL Server.
// Implementation omitted.
return 0;
}
}
Expected output:
Issue — Single Responsibility Principle: Calculating the total and persisting the order combine separate responsibilities if both are implemented in this method.
Recommendation: Separate persistence from calculation when doing so improves cohesion and testability.
Priority: Medium; assess the actual implementation before refactoring.
Input:
[HttpGet("{id}")]
public async Task<IActionResult> GetOrder(int id)
{
var order = await _dbContext.Orders
.FirstOrDefaultAsync(o => o.Id == id);
return order is null ? NotFound() : Ok(order);
}
Expected output:
Potential risk — Authorization: Verify that the endpoint enforces the appropriate authentication and order-level authorization policies.
Recommendation: Apply the relevant authorization policy and verify that the current user can access the requested order.
Priority: High if unauthorized users can access other customers' orders; otherwise, confirm existing safeguards before flagging a defect.
Review the following API method:
{{PASTE_CSHARP_API_METHOD_HERE}}
Return a short bullet-point summary containing only actionable findings.
For each finding, include:
Category: Bug, Security, Performance, SOLID, or Maintainability.
Issue: What is wrong and why it matters.
Recommendation: The smallest reasonable fix.
Priority: High, Medium, or Low.
If no meaningful issues are identified, state that clearly.
End with a one-sentence overall assessment. Do not claim the code is production-ready solely because no obvious issues were found.
Why this prompt is effective
prompt engineering improves the quality and consistency of the review, but it doesn't replace compilation, unit tests, integration tests, security testing, or measuring real performance.
You have now covered six important prompting techniques and practices:
Technique Remember it as
Zero-shot Instruction only
One-shot One example
Few-shot A few examples
Many-shot Many examples
Zero-shot CoT Request a careful, structured solution without examples
Few-shot CoT Demonstrate the solution pattern with worked examples
You also learned how triple quotes, tags, and headings can make prompts easier to read and maintain.
We'll combine the concepts into a repeatable method using your framework:
R — Role: How should the AI behave?
T — Task: What must it do?
C — Context and constraints: What background and rules matter?
F — Format: What should the output look like?