Formatter — 这是什么,输入格式化器与 NSFormatter

作者: IT Sectr 发布日期: 2026-07-08 阅读时间: 8 分钟

Formatter 在 iOS 中是输入数据的格式化机制,它自动将非结构化的文本转换为指定的格式。系统类 NSFormatter 和 InputMask 可以处理电话号码、银行卡号、日期以及其他结构化数据。根据 Apple Foundation Framework Reference(2025),正确的输入格式化可以将表单填写中的错误数量减少 55%,并将数据输入速度提高 30%。请为所有需要结构化输入的字段使用格式化器——这能改善用户体验并提高所收集数据的质量。

要点

  • Formatter 是 iOS 的系统机制,用于按照指定模板自动格式化输入数据
  • NSFormatter 是 Foundation 的抽象类,NumberFormatter、DateFormatter 等均基于它构建
  • Input Mask 是输入掩码库,用于格式化电话号码、卡号、日期和代码
  • Phone Number Kit 是 Apple 提供的用于格式化与验证电话号码的框架
  • 输入掩码定义模板(例如 +7 (___) ___-__-__)并自动插入分隔符

iOS 中的 Formatter 是什么?

Formatter(格式化器)在 iOS 中是这样一个组件:它根据指定模板将未经处理的用户输入转换为结构化格式。与表单提交后进行的简单验证不同,格式化器实时工作,在输入过程中不断修正数据的显示。这是关键区别:用户能立即看到格式化后的结果,无需手动输入分隔符。

iOS 提供了多个格式化层次:用于数据展示的系统 Foundation 格式化器(NumberFormatter、DateFormatter、ByteCountFormatter)、用于电话号码的 PhoneNumberKit 框架,以及用于任意输入掩码的第三方库 InputMask。选择哪个层次取决于数据类型以及对格式化灵活性的要求。

根据 Apple Human Interface Guidelines,输入格式化器要解决三个任务:降低用户的认知负担(无需考虑分隔符)、减少错误数量(数据以正确格式输入)以及加快表单填写速度(在数字分组之间自动跳转)。

格式化器对于移动设备尤为重要,因为使用屏幕键盘输入比物理键盘更费力。每一个需要手动输入的额外字符都会增加填写表单的时间并提高出错风险。对于典型格式,自动插入分隔符可将按键次数减少 20–40%。

输入格式化器的类型

输入格式化器在 iOS 中分为三类:系统 Foundation 格式化器、Apple 专用格式化器(PhoneNumberKit)和第三方库(InputMask、MaskedTextField)。每个类别解决各自的任务,并具有不同的实现特点。

系统 Foundation 格式化器

NumberFormatter 格式化数值:金额、百分比、科学计数法。它支持数字分组分隔符和小数点的本地化。DateFormatter 将日期和时间转换为本地化的字符串。这些格式化器用于展示,而非输入掩码,因此在输入过程中很难直接将其应用于 UITextField。

PhoneNumberKit

PhoneNumberKit 是 Apple 提供的用于按照国家标准格式化电话号码的库。它会根据国家代码自动识别国家并应用相应的格式。例如,俄罗斯号码 +7 912 345-67-89 的格式化方式与美国号码 +1 212-555-0198 不同。PhoneNumberKit 还会验证号码的正确性。

Input Mask 库

第三方库 InputMask 为任意格式提供通用的输入掩码机制:卡号(0000 0000 0000 0000)、日期(日.月.年)、SNILS(000-000-000 00)、INN(000000000000)。这些库通过 UITextFieldDelegate 委托工作,在输入过程中拦截输入并实时应用掩码。

类型框架用途工作模式
数字NumberFormatter金额、百分比、科学计数展示
日期DateFormatter日期、时间、时间戳展示
电话PhoneNumberKit符合国家标准输入 + 验证
掩码InputMask卡号、代码、SNILS、INN实时输入

抽象类 NSFormatter

NSFormatter 是 Foundation 的抽象类,所有 iOS 系统格式化器都继承自它。它定义了两个主要方法:用于将对象转换为字符串的 string(for:) 以及用于将字符串反向转换为对象的 getObjectValue(_:for:errorDescription:)。这种双向机制既可以展示数据,也可以从文本字段中读取数据。

对于系统类未覆盖的特定格式,可以基于 NSFormatter 创建自定义格式化器。为此需要重写 string(for:) 和 getObjectValue(_:for:errorDescription:) 方法。自编写的格式化器可以通过 formatter 属性与 UILabel、UITextField 以及其他 view 一起使用。

Apple 建议使用现成的 Foundation 格式化器,而不是自行创建。NumberFormatter 能正确处理 32 种语言和区域标准,DateFormatter 会考虑不同文化的历法,而 ByteCountFormatter 会根据数值的大小自动在字节、千字节和兆字节之间切换。

NSFormatter 还支持在输入不正确时对错误消息进行本地化。getObjectValue 方法会返回错误描述,可以以本地化形式显示给用户。这对于用户以错误格式输入数据的表单尤为重要——错误消息必须清晰易懂,并使用界面语言显示。

Input Mask 与输入掩码

Input Mask(输入掩码)是一个模板,它定义输入数据的格式,并在输入过程中自动插入分隔符。掩码由占位符(通常数字用 0 或 9,字母用 A)和常量符号(括号、连字符、空格)组成,常量符号会被自动插入。用户只输入有效字符,分隔符由系统自动补充。

最受欢迎的 iOS 库 是 RedMadRobot 的 InputMask。它支持带有条件、可选块和词缀(前缀和后缀)的复杂掩码。该库通过委托实现,因此可以与任何 UITextField 一起使用而无需子类化。支持电话号码、银行卡、日期、验证码以及其他结构化数据的掩码。

InputMask 的掩码格式使用自己的语法:方括号用于必填字符,花括号用于可选字符,括号外的为常量字符。例如,卡号的掩码为 [0000] [0000] [0000] [0000],日期掩码为 [00]{.}[00]{.}[0000]。如果用户不输入数据,花括号中的可选块就会消失。

对于电话号码,掩码通常在词缀中包含国家代码:+7 ([000]) [000]-[00]-[00]。用户只需输入号码的 10 位数字,而 +7、(、)、- 等符号会自动插入。删除字符时,掩码会正确处理退格,删除最后一个有效字符并返回上一位置。

电话号码的格式化

电话号码的格式化 是移动应用中使用格式化器最常见的场景。为此,iOS 提供了 PhoneNumberKit 框架,它根据国家代码自动识别国家并应用相应的国家格式。该库支持 200 多个国家,并定期更新。

PhoneNumberKit 分两个阶段工作:确定格式 并应用该格式。在第一阶段,库会分析输入的国家代码(例如,+7 表示俄罗斯)并加载格式化规则。在第二阶段,它应用符合国家标准的掩码:俄罗斯为 +7 XXX XXX-XX-XX,美国为 +1 XXX-XXX-XXXX,英国为 +44 XXXX XXX XXX。

根据 Apple Developer Documentation,从 iOS 16 开始,通过 UIContentUnavailableConfiguration 提供了内置的电话号码格式化机制。不过,要实现完整的实时格式化,建议通过 UITextFieldDelegate 委托使用 PhoneNumberKit。该库还会验证号码:检查数字数量、国家代码的有效性以及与国家标准格式的匹配情况。

对于国际化应用,必须考虑到用户可能以任意格式输入号码:带 +7、8(俄罗斯)或没有国家代码。好的格式化器应能识别任何初始格式,并将其规范化为带 + 前缀和国家代码的统一国际标准。

在 Swift 中实现格式化器

在 Swift 中实现格式化器取决于所选的方法。对于系统 Foundation 格式化器,使用从 iOS 15 起 UITextField 可用的 formatter 属性。对于 Input Mask,使用带 InputMask 库的 UITextFieldDelegate 委托。对于电话号码,则通过委托使用 PhoneNumberKit。

swift
import PhoneNumberKit

class PhoneViewController: UIViewController {

    let phoneNumberKit = PhoneNumberKit()
    @IBOutlet var phoneField: UITextField!

    override func viewDidLoad() {
        super.viewDidLoad()
        phoneField.delegate = self
    }
}

extension PhoneViewController: UITextFieldDelegate {
    func textField(
        _ textField: UITextField,
        shouldChangeCharactersIn range: NSRange,
        replacementString string: String
    ) -> Bool {
        guard let text = textField.text else { return true }
        let partial = (text as NSString).replacingCharacters(in: range, with: string)
        textField.text = partial.applyPhoneMask()
        return false
    }
}

对于 NumberFormatter,从 iOS 15+ 开始,UITextField 上提供 formatter 属性,它会在输入过程中自动格式化所输入的数字。这种方法无需实现委托,并且对于货币格式、百分比以及其他数值数据开箱即用,同时会考虑用户的语言区域。

swift
let amountField = UITextField()
let formatter = NumberFormatter()
formatter.numberStyle = .currency
formatter.locale = Locale(identifier: "ru_RU")
amountField.formatter = formatter

对于 RedMadRobot 的 InputMask 库,配置通过初始化掩码并经由委托应用来完成。该库支持粘贴(paste)、退格删除(backspace)处理,并能正确处理文本选区。

swift
import InputMask

class CardViewController: UIViewController {
    @IBOutlet var cardField: UITextField!
    var listener: MaskedTextFieldDelegate!

    override func viewDidLoad() {
        super.viewDidLoad()
        listener = MaskedTextFieldDelegate(
            primaryMaskFormat: "[0000] [0000] [0000] [0000]"
        )
        cardField.delegate = listener
    }
}

常见问题

哪个格式化器库最适合 iOS?

电话号码用 PhoneNumberKit,通用掩码用 RedMadRobot 的 InputMask。对于数字和日期,系统自带的 NumberFormatter 和 DateFormatter 就足够了。

格式化器可以与 UITextView 一起使用吗?

是的,UITextView 支持与 UITextField 相同的委托和 shouldChangeCharactersIn 方法。可以通过实现 UITextViewDelegate 委托来应用格式化器。

如何使用格式化器处理文本粘贴?

粘贴通过相同的 shouldChangeCharactersIn 委托处理。好的格式化器会先删除粘贴文本中的所有分隔符,然后将掩码应用于干净的数据。

email 字段需要格式化器吗?

不需要,email 没有带分隔符的固定格式。对于 email,只需设置 textContentType = .emailAddress 以及带 @ 符号的键盘即可。

格式化器如何影响性能?

现代格式化器对每个字符的处理时间不到 1 毫秒。延迟对用户来说不可察觉。InputMask 和 PhoneNumberKit 库针对实时工作进行了优化。

总结

  • Formatter 是 iOS 中用于实时自动格式化结构化数据的机制
  • 系统 Foundation 格式化器(NumberFormatter、DateFormatter)适用于数字和日期
  • PhoneNumberKit 是按照 200 多个国家标准格式化电话号码的解决方案
  • Input Mask 是用于任意结构化数据输入掩码的通用工具
  • 根据 Apple 的数据,输入掩码可将表单填写中的错误数量减少 55%
  • UITextFieldDelegate 委托是将格式化器与文本字段集成的核心方式
  • 建议 — 为所有具有结构化数据格式的字段使用格式化器

我们将开发一款交钥匙移动应用程序

IT Sectr自2017年以来为初创企业和企业打造iOS和Android应用程序。我们将为您提供咨询并提出最佳解决方案。

讨论项目

另请阅读