Initial commit

This commit is contained in:
2026-07-13 09:25:40 +07:00
parent c08ff54676
commit bccfb156d7
1938 changed files with 641646 additions and 0 deletions

View File

@@ -0,0 +1,272 @@
# Problem Query Methods - Giải Thích
## "Problem Query Methods" là gì?
**Problem Query Methods** là các methods trong class `Problem` dùng để **query (truy vấn) thông tin** về Problem, thay vì thay đổi trạng thái của Problem.
### Ví dụ:
-**Non-query methods** (thay đổi trạng thái):
- `AddParameterBlock()` - thêm parameter block
- `SetParameterBlockConstant()` - đặt parameter block thành constant
- `SetManifold()` - gán manifold cho parameter block
-**Query methods** (chỉ đọc thông tin):
- `HasParameterBlock()` - kiểm tra parameter block có tồn tại không
- `GetParameterBlockSize()` - lấy kích thước của parameter block
- `IsParameterBlockConstant()` - kiểm tra parameter block có constant không
- `HasManifold()` - kiểm tra parameter block có manifold không
- `GetManifoldHandle()` - lấy manifold handle của parameter block
---
## So Sánh: C Test vs C# Test
### C Test (`test_problem_query_methods`) - Test 11
C test có **explicit tests** cho tất cả query methods:
```c
// Test has_parameter_block
int has_block = ceres_wrapper_problem_has_parameter_block(problem, params);
TEST_ASSERT(has_block == 1, "Has parameter block");
// Test get_parameter_block_size
int size = ceres_wrapper_problem_get_parameter_block_size(problem, params);
TEST_ASSERT(size == 3, "Get parameter block size");
// Test is_parameter_block_constant
int is_constant = ceres_wrapper_problem_is_parameter_block_constant(problem, params);
TEST_ASSERT(is_constant == 0, "Parameter block is variable");
// Test has_manifold
int has_manifold = ceres_wrapper_problem_has_manifold(problem, params);
TEST_ASSERT(has_manifold == 0, "No manifold initially");
// Test get_manifold
ceres_manifold_t* manifold = ceres_wrapper_problem_get_manifold(problem, params);
TEST_ASSERT(manifold == NULL, "Get manifold returns NULL when no manifold");
// Test với non-existent parameter block
double fake_params[2] = {99.0, 99.0};
has_block = ceres_wrapper_problem_has_parameter_block(problem, fake_params);
TEST_ASSERT(has_block == 0, "Non-existent parameter block");
size = ceres_wrapper_problem_get_parameter_block_size(problem, fake_params);
TEST_ASSERT(size == -1, "Get size returns -1 for non-existent block");
```
### C# Test - Hiện Tại
C# test **chỉ có tests** cho:
-`IsParameterBlockConstant()` - có 2 tests
- `IsParameterBlockConstant_ShouldReturnFalse_WhenVariable`
- `IsParameterBlockConstant_ShouldReturnTrue_WhenConstant`
**Thiếu tests** cho:
-`HasParameterBlock()` - chưa có test
-`GetParameterBlockSize()` - chưa có test
-`HasManifold()` - chưa có test
-`GetManifoldHandle()` - chưa có test
-`GetParameterBlockTangentSize()` - chưa có test
---
## Tại Sao Cần Test Query Methods?
### 1. **Verify API Works Correctly**
Đảm bảo các methods trả về đúng giá trị:
- `HasParameterBlock()` trả về `true` khi parameter block tồn tại
- `GetParameterBlockSize()` trả về đúng kích thước
- `HasManifold()` trả về `true` sau khi set manifold
### 2. **Edge Cases**
Test các trường hợp đặc biệt:
- Query parameter block không tồn tại → trả về `false` hoặc `-1`
- Query manifold khi chưa set → trả về `false` hoặc `IntPtr.Zero`
- Query size của non-existent block → trả về `-1`
### 3. **Integration với Other Operations**
Verify query methods hoạt động đúng sau các operations:
- Sau `AddParameterBlock()``HasParameterBlock()` = `true`
- Sau `SetManifold()``HasManifold()` = `true`
- Sau `SetParameterBlockConstant()``IsParameterBlockConstant()` = `true`
---
## Các Methods Cần Test
### 1. `HasParameterBlock(double[] parameters)`
**Mục đích**: Kiểm tra parameter block có tồn tại trong Problem không
**Test cases cần có**:
```csharp
[Test]
public void HasParameterBlock_ShouldReturnTrue_WhenExists()
{
using var problem = new Problem();
var parameters = new double[] { 1.0, 2.0 };
problem.AddParameterBlock(parameters, parameters.Length);
var hasBlock = problem.HasParameterBlock(parameters);
Assert.That(hasBlock, Is.True);
}
[Test]
public void HasParameterBlock_ShouldReturnFalse_WhenNotExists()
{
using var problem = new Problem();
var parameters = new double[] { 1.0, 2.0 };
var fakeParams = new double[] { 99.0, 99.0 };
problem.AddParameterBlock(parameters, parameters.Length);
var hasBlock = problem.HasParameterBlock(fakeParams);
Assert.That(hasBlock, Is.False);
}
```
### 2. `GetParameterBlockSize(double[] parameters)`
**Mục đích**: Lấy kích thước của parameter block
**Test cases cần có**:
```csharp
[Test]
public void GetParameterBlockSize_ShouldReturnCorrectSize()
{
using var problem = new Problem();
var parameters = new double[] { 1.0, 2.0, 3.0 };
problem.AddParameterBlock(parameters, parameters.Length);
var size = problem.GetParameterBlockSize(parameters);
Assert.That(size, Is.EqualTo(3));
}
[Test]
public void GetParameterBlockSize_ShouldReturnMinusOne_WhenNotExists()
{
using var problem = new Problem();
var fakeParams = new double[] { 99.0, 99.0 };
var size = problem.GetParameterBlockSize(fakeParams);
Assert.That(size, Is.EqualTo(-1));
}
```
### 3. `HasManifold(double[] parameters)`
**Mục đích**: Kiểm tra parameter block có manifold không
**Test cases cần có**:
```csharp
[Test]
public void HasManifold_ShouldReturnFalse_WhenNoManifold()
{
using var problem = new Problem();
var parameters = new double[] { 1.0, 2.0, 3.0, 4.0 };
problem.AddParameterBlock(parameters, parameters.Length);
var hasManifold = problem.HasManifold(parameters);
Assert.That(hasManifold, Is.False);
}
[Test]
public void HasManifold_ShouldReturnTrue_WhenManifoldSet()
{
using var problem = new Problem();
var quaternion = new double[] { 0.0, 0.0, 0.0, 1.0 };
problem.AddParameterBlock(quaternion, quaternion.Length);
using var manifold = new QuaternionManifold();
problem.SetManifold(quaternion, manifold);
var hasManifold = problem.HasManifold(quaternion);
Assert.That(hasManifold, Is.True);
}
```
### 4. `GetManifoldHandle(double[] parameters)`
**Mục đích**: Lấy native handle của manifold (trả về `IntPtr.Zero` nếu không có)
**Test cases cần có**:
```csharp
[Test]
public void GetManifoldHandle_ShouldReturnZero_WhenNoManifold()
{
using var problem = new Problem();
var parameters = new double[] { 1.0, 2.0 };
problem.AddParameterBlock(parameters, parameters.Length);
var handle = problem.GetManifoldHandle(parameters);
Assert.That(handle, Is.EqualTo(IntPtr.Zero));
}
[Test]
public void GetManifoldHandle_ShouldReturnNonZero_WhenManifoldSet()
{
using var problem = new Problem();
var quaternion = new double[] { 0.0, 0.0, 0.0, 1.0 };
problem.AddParameterBlock(quaternion, quaternion.Length);
using var manifold = new QuaternionManifold();
problem.SetManifold(quaternion, manifold);
var handle = problem.GetManifoldHandle(quaternion);
Assert.That(handle, Is.Not.EqualTo(IntPtr.Zero));
}
```
### 5. `GetParameterBlockTangentSize(double[] parameters)`
**Mục đích**: Lấy tangent size của parameter block (khi có manifold)
**Test cases cần có**:
```csharp
[Test]
public void GetParameterBlockTangentSize_ShouldReturnTangentSize_WithManifold()
{
using var problem = new Problem();
var quaternion = new double[] { 0.0, 0.0, 0.0, 1.0 }; // 4D ambient
problem.AddParameterBlock(quaternion, quaternion.Length);
using var manifold = new QuaternionManifold(); // 3D tangent
problem.SetManifold(quaternion, manifold);
var tangentSize = problem.GetParameterBlockTangentSize(quaternion);
Assert.That(tangentSize, Is.EqualTo(3)); // Quaternion: 4D ambient → 3D tangent
}
```
---
## Kết Luận
### Hiện Tại
- ✅ C# API **đã implement** tất cả query methods
- ✅ C# test **đã có** test cho `IsParameterBlockConstant()`
- ❌ C# test **thiếu** tests cho 5 methods còn lại
### Khuyến Nghị
1. **Nên thêm tests** cho các query methods để:
- Đảm bảo API hoạt động đúng
- Test edge cases (non-existent blocks, null parameters)
- Verify integration với các operations khác
2. **Priority**:
- **High**: `HasParameterBlock()`, `GetParameterBlockSize()` - thường dùng
- **Medium**: `HasManifold()`, `GetManifoldHandle()` - dùng khi làm việc với manifolds
- **Low**: `GetParameterBlockTangentSize()` - ít dùng, nhưng nên có test
3. **Impact**:
- Không ảnh hưởng đến production (API đã implement đúng)
- Nhưng thiếu tests có thể dẫn đến bugs không được phát hiện khi refactor
---
**Last Updated**: 2024-12-19