news 2026/4/16 6:00:26

Fortran: 实现注册模式(Registry Pattern)

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Fortran: 实现注册模式(Registry Pattern)

文章目录

      • ✅ 核心思想
      • 📌 示例:注册名字 → 对象映射
      • 🧪 使用示例
      • 🔍 说明与扩展建议
      • ✅ 总结

在 Fortran(特别是 Fortran 2003 及以后支持面向对象特性的版本)中,虽然没有像 C++ 或 Python 那样原生的“注册模式”(Registry Pattern)语法糖,但可以借助派生类型(derived types)指针(pointers)可分配变量(allocatable components)来实现类似功能:将一个对象“注册”到另一个对象中,并支持查询和变更。

Design patterns
https://github.com/farhanjk/FortranPatterns

下面是一个典型的实现思路和示例代码:


✅ 核心思想

  • 使用一个容器类型(如Registry)来保存一组被注册的对象(通过指针或 allocatable 组件)。
  • 提供registerlookupupdate等过程(即方法)。
  • 利用 Fortran 的类型绑定过程(type-bound procedures)实现面向对象风格。

📌 示例:注册名字 → 对象映射

module registry_mod implicit none private public :: Item, Registry type :: Item integer :: value = 0 contains procedure :: set_value procedure :: get_value end type Item type :: Registry private type(Item), pointer :: items(:) => null() character(len=:), allocatable :: keys(:) integer :: n = 0 integer, parameter :: initial_capacity = 10 contains procedure :: register_item procedure :: lookup_item procedure :: update_item final :: finalize_registry end type Registry contains subroutine set_value(this, val) class(Item), intent(inout) :: this integer, intent(in) :: val this%value = val end subroutine set_value function get_value(this) result(val) class(Item), intent(in) :: this integer :: val val = this%value end function get_value subroutine register_item(this, key, item) class(Registry), intent(inout) :: this character(len=*), intent(in) :: key type(Item), intent(in) :: item integer :: i ! 检查是否已存在 do i = 1, this%n if (this%keys(i) == key) then error stop 'Key already exists: ' // trim(key) end if end do ! 扩容 if (.not. associated(this%items)) then allocate(this%items(this%initial_capacity)) allocate(this%keys(this%initial_capacity), source='') else if (this%n >= size(this%items)) then call resize(this) end if this%n = this%n + 1 this%keys(this%n) = key this%items(this%n) = item end subroutine register_item function lookup_item(this, key) result(item_ptr) class(Registry), intent(in) :: this character(len=*), intent(in) :: key type(Item), pointer :: item_ptr integer :: i item_ptr => null() do i = 1, this%n if (this%keys(i) == key) then item_ptr => this%items(i) return end if end do end function lookup_item subroutine update_item(this, key, new_item) class(Registry), intent(inout) :: this character(len=*), intent(in) :: key type(Item), intent(in) :: new_item integer :: i do i = 1, this%n if (this%keys(i) == key) then this%items(i) = new_item return end if end do error stop 'Key not found for update: ' // trim(key) end subroutine update_item subroutine resize(this) class(Registry), intent(inout) :: this type(Item), allocatable :: temp_items(:) character(len=:), allocatable :: temp_keys(:) integer :: old_size, new_size old_size = size(this%items) new_size = old_size * 2 allocate(temp_items(new_size)) temp_items(1:old_size) = this%items deallocate(this%items) this%items => temp_items allocate(temp_keys(new_size), source='') temp_keys(1:old_size) = this%keys deallocate(this%keys) this%keys = temp_keys end subroutine resize subroutine finalize_registry(this) type(Registry), intent(inout) :: this if (associated(this%items)) deallocate(this%items) if (allocated(this%keys)) deallocate(this%keys) end subroutine finalize_registry end module registry_mod

🧪 使用示例

program test_registry use registry_mod implicit none type(Registry) :: reg type(Item), pointer :: p => null() type(Item) :: tmp ! 注册 call tmp%set_value(42) call reg%register_item('answer', tmp) ! 查询 p => reg%lookup_item('answer') if (associated(p)) then print *, 'Found value:', p%get_value() end if ! 更新 call tmp%set_value(100) call reg%update_item('answer', tmp) p => reg%lookup_item('answer') if (associated(p)) then print *, 'Updated value:', p%get_value() end if end program test_registry

🔍 说明与扩展建议

  • 键值对:当前使用character作为 key,也可替换为整数 ID 或其他类型。
  • 指针 vs allocatable:这里items用指针数组便于返回引用;若只存副本,可用allocatable
  • 线程安全:Fortran 本身不提供线程安全机制,如需多线程需加锁(例如通过 OpenMP critical)。
  • 泛型支持:Fortran 不支持模板,若需注册不同类型,可考虑:
    • 使用class(*)+select type(但复杂)
    • 为每种类型写专用 Registry
    • 或使用预处理器(如 fypp)生成代码

✅ 总结

Fortran 2003+ 完全可以实现注册模式,核心是:

  • 用派生类型封装注册表
  • 用指针/数组存储对象
  • 提供注册、查找、更新接口
  • 利用 finalizer 自动清理资源
版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/3/31 11:01:58

Memo智能笔记:VSCode知识管理革命

Memo智能笔记:VSCode知识管理革命 【免费下载链接】memo Markdown knowledge base with bidirectional [[link]]s built on top of VSCode 项目地址: https://gitcode.com/gh_mirrors/memo/memo 在信息爆炸的时代,如何高效管理个人知识成为每个学…

作者头像 李华
网站建设 2026/4/14 12:51:56

翻译结果差异分析:同一模型多次输出

翻译结果差异分析:同一模型多次输出 📖 背景与问题提出 在实际使用 AI 智能中英翻译服务的过程中,用户可能会观察到一个看似反常的现象:对完全相同的中文输入,同一 CSANMT 模型在不同时间或连续请求下,生…

作者头像 李华
网站建设 2026/4/11 0:35:16

6种字重苹方字体:跨平台字体统一终极解决方案

6种字重苹方字体:跨平台字体统一终极解决方案 【免费下载链接】PingFangSC PingFangSC字体包文件、苹果平方字体文件,包含ttf和woff2格式 项目地址: https://gitcode.com/gh_mirrors/pi/PingFangSC 还在为网页在不同操作系统上字体显示不一致而烦…

作者头像 李华
网站建设 2026/4/4 22:38:09

CRNN模型推理延迟优化:CPU环境下提速50%的方法

CRNN模型推理延迟优化:CPU环境下提速50%的方法 📖 背景与挑战:OCR文字识别的工程落地瓶颈 光学字符识别(OCR)作为计算机视觉中的经典任务,广泛应用于文档数字化、票据识别、车牌提取等场景。在实际部署中&a…

作者头像 李华
网站建设 2026/4/15 6:04:04

PDF补丁丁:5分钟快速上手的高效PDF编辑神器

PDF补丁丁:5分钟快速上手的高效PDF编辑神器 【免费下载链接】PDFPatcher PDF补丁丁——PDF工具箱,可以编辑书签、剪裁旋转页面、解除限制、提取或合并文档,探查文档结构,提取图片、转成图片等等 项目地址: https://gitcode.com/…

作者头像 李华
网站建设 2026/4/8 18:21:03

好写作AI:专治论文“逻辑硬伤”,你的AI级学术CT机

当你的论文逻辑开始“鬼打墙”,一个好用的专属模型,就是照亮迷宫的那盏灯。“这段……和上一段有什么关系?” “你的论点是怎么推导出这个结论的?” “整篇文章读下来,怎么感觉在几个点之间反复横跳?”如果…

作者头像 李华