- iOS/Objective-C 元类和类别
- objective-c - -1001 错误,当 NSURLSession 通过 httpproxy 和/etc/hosts
- java - 使用网络类获取 url 地址
- ios - 推送通知中不播放声音
我正在经历对现有代码进行单元测试的过程,该代码在编写时并未考虑单元测试。
有几个类的结构是这样的:
class Texture
{
public:
friend class Model;
private:
void Load( int a, int b);
void Update(int a, int b);
void Use(int a, int b);
}
class Material
{
public:
friend class Model;
private:
void Load(int a);
void Update(int a);
void Use(int a);
}
class Mesh
{
public:
friend class Model;
private:
void Load(int a, int b, int c);
void Update(int a, int b, int c);
void Use(int a, int b, int c);
}
class Model
{
public:
void Load(); // call all the individual Load()
void Use(); // call all the individual Use()
}
它们保持私有(private)的原因是因为它的设计方式只有模型类才能调用它们,因此是 friend 。
[在实际代码中有一个 Attorney-Client 习惯用法,它限制了 Model 对这些类的访问,但我将其排除在代码片段之外]
现在我正在尝试对这些类进行单元测试。在弄清楚如何测试这些私有(private)函数时,我遇到了 Iceberg Class 的术语。我觉得上面的类(class)在某种程度上是有罪的。
大多数涉及该主题的文章还提到,如果需要测试一个私有(private)函数,这主要意味着该类过度了,这些函数最好放在另一个独立的类中,让它们保持公共(public)状态。
所以现在,我不确定这是一个糟糕的代码设计,我应该重新设计它们以使单元测试更容易,还是我只是继续进行单元测试。
想听听大家的意见
最佳答案
为了使这段代码可测试,我将引入三个纯虚拟接口(interface)(ITexture
、IMesh
、IMaterial
)并添加一个免费的创建此类接口(interface)(例如 getTexture
)的方法,该接口(interface)将返回类型为 ITexture
的 smart_ptr。然后在 cpp 文件中实现 get[...]
方法并在生产代码中使用它来创建 Model
对象。在单元测试中,我会为每个接口(interface)类创建一个模拟,并对注入(inject)的模拟设置适当的期望(例如,使用 gmock
或编写您自己的模拟)。
Mesh
示例,头文件 IMesh.hpp:
class IMesh {
public:
virtual ~IMesh() = default;
virtual void Load(int a, int b, int c) = 0;
virtual void Update(int a, int b, int c) = 0;
virtual void Use(int a, int b, int c) = 0;
};
std::unique_ptr<MeshI> getMesh(/*whatever is needed to create mesh*/);
实现文件,MeshImpl.cpp:
#include "IMesh.hpp";
class Mesh : public IMesh {
public:
Mesh(/*some dependency injection here as well if needed*/);
void Load(int a, int b, int c) override;
void Update(int a, int b, int c) override;
void Use(int a, int b, int c) override;
};
Mesh::Mesh(/*[...]*/) {/*[...]*/}
void Mesh:Load(int a, int b, int c) {/*[...]*/}
void Mesh:Update(int a, int b, int c) {/*[...]*/}
void Mesh:Use(int a, int b, int c) {/*[...]*/}
依赖注入(inject):
Model model{getMesh(), getTexture(), getMaterial()};
通过这种方法可以实现:
Model
类 - 因为接口(interface)中的所有方法都必须是 public
以便 Model
类使用它,您现在可以分别测试每个接口(interface)IMesh
的不同实现,并在需要时将其注入(inject)模型。有关 DI 技术的更多详细信息,请参阅 this question
关于c++ - Iceberg 类和 Google 单元测试,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56536150/
如何为现有的未分区的 Iceberg 表添加分区?表格已加载数据。 表已创建: import org.apache.iceberg.hive.HiveCatalog import org.apache
背景 在B站,每天都有PB级的数据注入到大数据平台,经过离线或实时的ETL建模后,提供给下游的分析、推荐及预测等场景使用。面对如此大规模的数据,如何高效低成本地满足下游数据的分析需求,一直是我们重点的
我正在经历对现有代码进行单元测试的过程,该代码在编写时并未考虑单元测试。 有几个类的结构是这样的: class Texture { public: friend class Model; pr
我正在尝试在 Windows 10 中设置 Pharo8 图像,使用我手动克隆的 git 存储库,但是 pharo 给出了一个奇怪的错误。以下代码在 linux 上运行良好,但在 Windows 上运
我有一个带有 2 个 Parquet 文件的冰山表,在 s3 中存储 4 行我尝试了以下命令: val tables = new HadoopTables(conf); val table = tab
我想将 Trino 与 Iceberg 表和 Azure ADLS/Blob 存储一起使用,而不是 S3。 我能够成功连接到 S3,例如 connector.name=iceberg iceberg.
我尝试在 Databricks 环境中设置 Apache Iceberg,但在 Spark SQL 中执行 MERGE 语句时遇到错误。 此代码: CREATE TABLE iceberg.db.ta
我尝试在 Databricks 环境中设置 Apache Iceberg,但在 Spark SQL 中执行 MERGE 语句时遇到错误。 此代码: CREATE TABLE iceberg.db.ta
我是一名优秀的程序员,十分优秀!