14、优化Apex与Visualforce代码编写的实用指南

优化Apex与Visualforce代码编写的实用指南

在开发过程中,编写高效、安全且易于维护的代码至关重要。本文将深入探讨Apex和Visualforce代码编写的相关技巧,帮助开发者提升代码质量。

1. 让类了解测试上下文

在Apex(触发器、批处理或控制器)代码中,有时需要知道代码是在正常执行还是在测试模式下执行。这一点非常重要,因为某些操作在测试模式下是不允许的,例如Web服务调用。可以使用 Test.isRunningTest() API为测试用例提供模拟数据。更多信息可参考: http://www.salesforce.com/us/developer/docs/apexcode/Content/apex_classes_restful_http_testing.htm

2. Apex REST Web服务

Apex提供了简单的注解,如 @RestResource @HttpPost @HttpGet ,可将任何类作为RESTful Web服务公开。以下是一些重要的注意事项:
- 使用 with sharing 关键字 :在声明Web服务类时,通常应使用 with sharing 关键字。在特殊情况下,可以使用 without sharing 绕过安全限制(如共享规则等),但这应在极端情况下进行,因为这样做会破坏安全性。
- 强制执行CRUD/FLS设置 :使用Force.com ESAPI或Apex描述信息在Apex REST中强制执行CRUD/FLS设置,这些设置默认不会强制执行。
- 利用 RestContext :该类可以让你处理入站的 RestRequest 和出站的 RestResponse 对象。

3. REST Web服务的API版本控制

Force.com的API版本控制做得很好,能够保持旧版本的向后兼容性。在Apex中也可以轻松实现相同的功能。例如,假设这是REST服务和Apex类的第一个版本:

@RestResource(urlMapping='/CoolestApexService/v1/*')
global with sharing class CoolestApexService
{
…
}

如果在API的v2版本中,Apex代码和API有重大更改,为了不破坏依赖v1版本API的客户端代码,可以创建上述Apex类的副本,并在副本中进行重大更改,同时保持向后兼容性。示例如下:

@RestResource(urlMapping='/CoolestApexService/v2/*')
global with sharing class CoolestApexServiceV2
{
…
}

请注意,这里重命名了类和REST注解的URL映射。

4. 了解限制

在某些情况下,了解给定上下文中的可用限制非常重要。这里的上下文指的是执行上下文,在Visualforce页面控制器、触发器、匿名块和测试用例中可能会有所不同。例如,堆大小限制通常为6 MB,但在电子邮件服务中则变为36 MB。

除了可用的总限制外,Apex运行时还会提供执行过程中到目前为止已消耗的限制的详细信息。可以使用 Limits 系统类来了解各种因素的总限制和已消耗的限制,例如:
- 脚本语句
- 堆大小
- SOQL查询数量

以下是一个示例代码,展示了如何使用 Limits API来了解可用的SOQL调用:

// Prints 100.
System.debug('Available Queries : ' + (Limits.getLimitQueries() - 
Limits.getQueries()));
// Consume 1 Query limit out of typical quota of 100
Contact[] contacts = [Select Id from Contact];
// Consume 1 more Query limit out of typical quota of 100
Account[] accounts = [Select Id from Account];
// Prints 98 now.
System.debug('Available Queries : ' + (Limits.getLimitQueries() - 
Limits.getQueries()));

要了解更多关于 Limits 系统类及其方法的信息,请参考: http://www.salesforce.com/us/developer/docs/apexcode/Content/apex_methods_system_limits.htm

5. 跟踪资源(限制)使用情况

了解并关注Apex代码消耗的各种平台资源/限制配额是一个很好的做法。与其他语言(如Java)一样,要跟踪资源使用情况,需要检查调试日志。如果你之前从未使用过调试日志,建议先阅读以下文章:
- 理解调试日志
- 设置调试日志过滤器

调试日志可以在以下两个位置进行检查:
- 在设置区域使用调试日志 :可以通过导航到“Your Name | Setup | Monitoring | Debug Logs”来为给定用户启用日志记录。点击“New”按钮,为给定用户启用日志记录。启用日志记录后,所有代码执行(控制器、触发器、批处理、未来方法等)都可以在“Debug Logs”网格中看到。要查看资源使用的详细信息,可以点击任何日志记录的“View”链接。在日志详细信息中,最后一部分显示了各种平台资源的累积使用情况。任何接近限制的资源使用都是一个很好的提示,需要在生产崩溃之前调整应用程序。建议及时进行必要的重构或清理,以保留足够的资源限制余量。更多详细信息,请参考: 查看调试日志
- 使用开发者控制台的日志记录功能 :与上述调试方法类似,可以使用开发者控制台进行相同的操作。要了解更多关于使用开发者控制台查看调试日志的信息,请查看完整指南: http://www.salesforce.com/us/developer/docs/apexcode/Content/apex_debugging_system_log_console.htm

6. Visualforce架构

Visualforce(VF)是Force.com创建自定义屏幕的方式。来自.NET和JEE(特别是JSF)背景的开发者会发现自定义标签、视图状态和回发有很多相似之处。与Apex一样,重要的是要理解VF页面在多租户环境中执行。因此,没有人拥有服务器,也不能编写需要数分钟来处理同步作业的页面。始终有一个监管者监视页面的资源消耗,如果VF页面消耗超过限制,将会停止显示。

在开始编码之前,通常最好先了解VF架构和执行顺序。以下是一些获取更多信息的链接:
- Visualforce架构
- Visualforce页面的执行顺序

在VF开发中,最重要的是要理解缓存行为和会话管理,这与其他语言/平台(如Java、.NET和PHP等)不同。以下是与Java(J2EE/JEE)的比较:
| 比较项 | Java(J2EE/JEE) | Force.com平台 |
| ---- | ---- | ---- |
| 缓存类/页面定义 | Java服务器将所有类定义缓存在内存(RAM/堆)中。通常,在首次请求时,如果JSP页面未编译/缓存,它将被转换为Java类定义并缓存在堆中。下次请求该页面时,堆中的缓存副本将进行渲染。 | 由于平台的多租户性质,无法将定义保留在内存中。编译后的类/页面定义存储在数据库(元数据存储库)中。为了处理页面请求,编译后的定义将加载到内存中以渲染页面。 |
| 会话管理 | Java服务器提供了多种会话管理方式,并完全控制更改它。开发者也可以调整或替换服务器的会话管理。例如,绕过cookie、使用隐藏字段、URL重写等。 | 平台负责会话管理,开发者无需担心。由于平台符合行业领先的安全标准,为了保护客户数据,Salesforce不允许你调整/替换会话管理。 |
| 会话存储 | 开发者可以在请求绑定的全局变量(如Session或HttpSession)中缓存一些数据,并在每次请求时根据需要访问它。 | 由于多租户性质,开发者没有像Session这样的全局变量可用,因此无法进行请求绑定的数据缓存。Visualforce使用一种可扩展的无状态机制,称为ViewState,通常用于存储流程所需的请求数据。 |

7. 重用平台的原生外观和感觉

在创建VF页面时,有一个非常基本且重要的用户体验(UX)方面需要考虑。我见过一些开发者在样式上过于花哨,但在这个平台上这并没有帮助;VF页面的最终用户大多是现有的Salesforce客户(99%的时间)。因此,如果VF页面与原生外观和感觉不相似,就会变得不直观,并且会带来培训问题。

以下是一些使用关键组件使VF页面看起来更像原生页面的技巧:
- 使用原生标题开始页面设计 <apex:sectionHeader> 组件常被许多Force.com开发者忽略,但它是实现原生外观和感觉的第一步。它会添加一个标题部分,包含页面标题和副标题。例如,以下代码展示了如何使用该标签为Case标准对象的页面添加原生外观和感觉:

<apex:pagestandardController="Case">
<apex:sectionHeader title="Cases" subtitle="De-dupe cases"/>
<apex:pageBlock title="Select cases">
<!-- Your code goes here -->
</apex:pageBlock>
</apex:page>
  • 创建原生详细信息部分/表单 :各种组件,如 <apex:pageBlock> <apex:pageBlockSection> <apex:pageBlockTable> <apex:inputField> 可以帮助你快速布局原生外观的详细信息部分。在大多数页面中,这些组件将是 <apex:sectionHeader> 组件之后的第二个构建块。例如,以下代码片段使用几行VF代码创建了一个新的Case屏幕,其外观和感觉与原生屏幕非常相似:
<apex:pagestandardController="Case">
<apex:sectionHeader title="Cases" subtitle="New Custom Case Screen"/>
  <apex:form>
    <apex:pageBlock title="Create New Case" mode="edit">
      <apex:pageBlockSection title="Case Basic Info">
      <apex:inputField value="{!Case.AccountId}"/>
      <apex:inputField value="{!Case.Status}"/>
      <apex:inputField value="{!Case.ContactId}"/>
      <apex:inputField value="{!Case.priority}"/>
      <apex:inputField value="{!Case.Origin}"/>
      </apex:pageBlockSection>
        <apex:pageBlockSection title="Other Case section">
        <!-- Add more fields here -->
      </apex:pageBlockSection>
      <apex:pageBlockButtons>
        <apex:commandButton value="Save" action="{!save}"/>
        <apex:commandButton value="Cancel" action="{!cancel}"/>
      </apex:pageBlockButtons>
    </apex:pageBlock>
  </apex:form>
</apex:page>

使用 <apex:pageBlockSection> 组件的 columns 属性可以帮助将布局从默认的两列更改为更高或更低的值。
- 将表格样式设置为原生网格 :类似地, <apex:pageBlockTable> 等组件可用于获取具有原生外观和感觉的网格/表格。最好的部分是,这个组件与sObjects配合得很好,因此它会自动将列标题作为主题字段标签(无需额外代码)。例如:

<apex:pageBlockTable value="{!account.Contacts}" var="con">
  <apex:column value="{!con.name}"/>
  <apex:column value="{!con.Title}"/>
  <apex:column value="{!con.Email}"/>
  <apex:column value="{!con.phone}"/>
</apex:pageBlockTable>
  • 以原生样式打印消息 :在VF中以原生外观和感觉显示信息、警告或错误类型的消息非常简单。开发者可以使用 <apex:pageMessage/> 标签直接在页面中打印消息。例如,以下单行代码可以显示一条原生外观的信息性消息:
<apex:pageMessage summary="Your job is queued for processing, email 
notification would be sent on completion" severity="info" strength="3" 
/>

如果需要,可以通过Apex添加消息并在VF页面上显示:
- 控制器

public void onValidate() {     
  if (event.Registeration_Deadline__c < System.now()){
    ApexPages.addMessage(new 
    ApexPages.Message(ApexPages.Severity.ERROR, 
    'Registration for this event is closed now.'));
  }  
  ...
}
- **VF页面**:需要重新渲染`<apex:pageMessages/>`组件。

始终在几乎所有VF AJAX调用中重新渲染 <apex:pageMessages> 组件。这样做有助于在很多情况下优雅地捕获用户和平台生成的消息。根据不同的情况(如确认、错误、致命、信息和警告),尝试在Apex和Visualforce中使用各种严重级别。

8. 原生(标准)与自定义控制器/扩展

标准控制器为开发者提供了丰富的平台功能。它们有两种类型:标准控制器和标准列表控制器。前者适用于处理单个记录,后者适用于处理记录列表。从高层次来看,它们提供以下关键功能:
- 自动处理安全性 :自动处理用户的FLS(字段级安全)和其他权限相关的安全性。
- 轻松访问对象字段 :标准控制器无需编写任何查询代码,即可轻松访问对象字段,包括父级和子级关系。标准控制器会检测页面中使用的字段并透明地查询它们。你可以在 这里 了解更多信息。
- 标准CRUD操作和列表操作 :提供标准的CRUD操作(如保存、快速保存、编辑、删除)和带分页的列表操作(下一页、上一页、第一页、最后一页)。以下链接来自Apex开发者指南,提供了可用方法的完整信息:
- 标准控制器
- 标准列表控制器

通常的经验法则是,尽可能充分利用标准控制器。以下是VF开发者指南中的一些代码片段,展示了标准控制器的功能:
- 标准列表控制器的分页
- 标准列表控制器的编辑数据

除了上述所有功能外,在某些情况下可能需要使用自定义控制器,例如:
- 一个复杂的页面需要同时对多个对象类型执行DML操作,例如,一个页面在点击“保存”按钮时创建一个账户和多个关联的联系人。
- 页面流程中需要进行Web服务调用。
- 需要通过Apex发送电子邮件。

即使在上述情况下,Force.com开发者也应该首先尝试使用自定义控制器扩展来解决问题,因为扩展保留了大部分标准功能,并根据需要添加新功能。例如,以下代码片段展示了如何使用扩展查询股票价格,同时保留原生功能:

<apex:pagestandardController="Account" extensions="DynamicBindingExt">
  <apex:pageMessage summary="Stock price for {!Account.Name} is 
  {!stockPrice}" severity="info" strength="3" />
  <apex:detail subject="{!account.id}" />
</apex:page>
public with sharing class DynamicBindingExt {
  public Decimal stockPrice{get;set;}
  public DynamicBindingExt(ApexPages.StandardController controller) {
    Account acc = (Account)controller.getRecord();
    String recordName = acc.Name;
    // stockPrice = result from HTTP callout based on account name
  }
}

关键要点是,除非确实需要,否则避免使用自定义控制器。这并不意味着自定义控制器没有用处,但关键是要尽可能利用标准平台的优势。

9. 重用VF代码

在VF中重用代码非常重要,特别是在中型和大型项目中,多个开发者可能会通过以下方式重复造轮子:
- 反复编写相同的标记和逻辑。
- 在不同页面之间复制粘贴VF代码。

通过遵循上述关于Apex和Visualforce代码编写的技巧,开发者可以提高代码的质量、安全性和可维护性,从而在AppExchange列表或生产部署中更加轻松。同时,合理利用标准功能和重用代码可以提高开发效率,减少错误。

优化Apex与Visualforce代码编写的实用指南

10. 避免过多复制粘贴,重用代码

为了避免在VF开发中进行过多的复制粘贴,实现代码重用,可以采用以下几种方式:
- 组件化开发 :将常用的页面元素封装成组件,例如一个包含特定样式和功能的表单组件。在不同页面中可以直接引用这些组件,减少重复代码。以下是一个简单的组件示例:

<!-- 定义组件 -->
<apex:component>
    <apex:pageBlock title="Common Form">
        <apex:inputField value="{!someField}" />
        <apex:commandButton value="Submit" action="{!submitAction}" />
    </apex:pageBlock>
</apex:component>
<!-- 在页面中引用组件 -->
<apex:page>
    <c:CommonForm />
</apex:page>
  • 使用模板 :创建通用的页面模板,包含页面的基本结构和样式,如页眉、页脚等。不同的页面可以基于这些模板进行扩展,只需要关注页面的具体内容。例如:
<!-- 定义模板 -->
<apex:page>
    <apex:sectionHeader title="Template Page" />
    <apex:insert name="body" />
    <apex:sectionFooter />
</apex:page>
<!-- 使用模板的页面 -->
<apex:page template="c:MyTemplate">
    <apex:define name="body">
        <!-- 页面具体内容 -->
        <apex:pageBlock title="Content">
            <apex:inputField value="{!anotherField}" />
        </apex:pageBlock>
    </apex:define>
</apex:page>
11. 限制视图状态

视图状态(ViewState)是Visualforce用于在请求之间保存页面数据的机制。过多的视图状态会导致页面性能下降,因此需要对其进行限制。以下是一些限制视图状态的方法:
- 减少不必要的数据存储 :只在视图状态中存储必要的数据,避免存储大量的临时数据或不需要跨请求保留的数据。例如,在控制器中使用瞬态(transient)关键字标记不需要存储在视图状态中的变量:

public class MyController {
    public transient List<SomeObject> tempList; // 该列表不会存储在视图状态中
    public List<SomeObject> importantList; // 重要数据会存储在视图状态中

    public MyController() {
        tempList = new List<SomeObject>();
        importantList = new List<SomeObject>();
    }
}
  • 使用AJAX进行局部更新 :通过AJAX调用只更新页面的部分内容,而不是整个页面。这样可以减少视图状态的传输和存储。例如:
<apex:page>
    <apex:form>
        <apex:outputPanel id="panel">
            <apex:inputField value="{!someField}" />
            <apex:commandButton value="Update" action="{!updateAction}" reRender="panel" />
        </apex:outputPanel>
    </apex:form>
</apex:page>
12. 通过字段集编写灵活页面

字段集(FieldSets)是一种在Salesforce中定义一组字段的方式。通过使用字段集,可以使VF页面更加灵活,能够根据不同的需求动态显示字段。以下是使用字段集的步骤:
1. 创建字段集 :在对象设置中创建字段集,选择要包含的字段。
2. 在VF页面中引用字段集

<apex:page standardController="Account">
    <apex:form>
        <apex:pageBlock title="Account Details">
            <apex:pageBlockSection title="Field Set Section">
                <apex:repeat value="{!$ObjectType.Account.FieldSets.MyFieldSet}" var="field">
                    <apex:inputField value="{!Account[field]}" />
                </apex:repeat>
            </apex:pageBlockSection>
        </apex:pageBlock>
    </apex:form>
</apex:page>

通过这种方式,当需要更改显示的字段时,只需要在字段集中进行修改,而不需要修改页面代码。

13. 加速AJAX调用

为了提高AJAX调用的速度,可以采取以下措施:
- 优化查询 :在AJAX调用涉及的数据查询中,确保查询语句高效。避免不必要的字段查询和复杂的条件。例如:

public class MyAjaxController {
    public List<Contact> getContacts() {
        // 只查询必要的字段
        return [SELECT Id, Name, Email FROM Contact LIMIT 10];
    }
}
  • 减少数据传输量 :只返回AJAX调用所需的数据,避免返回过多的冗余数据。可以在控制器中对数据进行处理和筛选。
  • 使用缓存 :对于一些不经常变化的数据,可以使用缓存机制,减少重复查询。例如:
public class MyAjaxController {
    private static Map<Id, Contact> contactCache;

    public List<Contact> getContacts() {
        if (contactCache == null) {
            contactCache = new Map<Id, Contact>([SELECT Id, Name, Email FROM Contact LIMIT 10]);
        }
        return contactCache.values();
    }
}
14. 充分利用全局变量

Salesforce提供了一些全局变量,如 $User $Label $ObjectType 等。合理利用这些全局变量可以简化代码,提高开发效率。以下是一些常见全局变量的使用示例:
- $User :获取当前用户的信息,如用户名、用户ID等。

<apex:page>
    <p>Welcome, {!$User.Name}</p>
</apex:page>
  • $Label :用于国际化和本地化,获取自定义标签的值。
<apex:page>
    <p>{!$Label.MyCustomLabel}</p>
</apex:page>
  • $ObjectType :获取对象的元数据信息,如字段列表、记录类型等。
<apex:page>
    <apex:repeat value="{!$ObjectType.Account.FieldSets.MyFieldSet}" var="field">
        <apex:inputField value="{!Account[field]}" />
    </apex:repeat>
</apex:page>
15. 避免JavaScript远程调用的常见错误

JavaScript远程调用(JavaScript Remoting)是一种在Visualforce页面中调用Apex方法的技术。在使用时需要注意以下常见错误:
- 方法签名问题 :确保Apex方法的签名与JavaScript调用中的参数和返回类型一致。例如:

// Apex方法
global with sharing class MyRemoteClass {
    @RemoteAction
    public static String getMessage(String param) {
        return 'Hello, ' + param;
    }
}
// JavaScript调用
Visualforce.remoting.Manager.invokeAction(
    '{!$RemoteAction.MyRemoteClass.getMessage}',
    'World',
    function(result, event) {
        if (event.status) {
            alert(result);
        } else {
            alert('Error: ' + event.message);
        }
    },
    {escape: true}
);
  • 安全性问题 :对远程调用的方法进行适当的权限检查,避免未经授权的访问。可以在Apex方法中添加权限验证逻辑。
  • 错误处理 :在JavaScript中对远程调用的结果进行充分的错误处理,确保在出现错误时能够给用户友好的提示。
16. 注意Visualforce页面的安全性

在开发Visualforce页面时,安全性至关重要。以下是一些安全方面的注意事项:
- 输入验证 :对用户输入进行严格的验证,防止SQL注入、XSS攻击等。可以使用Apex的验证规则或JavaScript进行前端验证。
- 访问控制 :确保只有授权用户能够访问页面和执行相关操作。可以使用标准控制器的安全功能或自定义的访问控制逻辑。
- 数据加密 :对于敏感数据,如密码、信用卡信息等,进行加密存储和传输。

17. 其他杂项技巧

除了上述内容,还有一些关于图表、动态VF组件、PDF渲染等方面的技巧:
- 图表 :使用 <apex:chart> 组件可以轻松创建各种图表,如柱状图、折线图等。例如:

<apex:page>
    <apex:chart data="{!chartData}" width="400" height="300">
        <apex:axis type="Category" position="bottom" fields="label" title="Labels" />
        <apex:axis type="Numeric" position="left" fields="value" title="Values" />
        <apex:barSeries orientation="vertical" xField="label" yField="value" />
    </apex:chart>
</apex:page>
  • 动态VF组件 :可以在运行时动态创建和添加VF组件。例如,根据用户的选择动态显示不同的表单。
public class DynamicComponentController {
    public Component.Apex.OutputPanel getDynamicPanel() {
        Component.Apex.OutputPanel panel = new Component.Apex.OutputPanel();
        panel.id = 'dynamicPanel';
        if (someCondition) {
            Component.Apex.InputField input = new Component.Apex.InputField();
            input.value = '{!someField}';
            panel.childComponents.add(input);
        }
        return panel;
    }
}
<apex:page controller="DynamicComponentController">
    <apex:dynamicComponent componentValue="{!dynamicPanel}" />
</apex:page>
  • PDF渲染 :使用 <apex:page renderAs="pdf"> 可以将页面渲染为PDF文件。可以设置页面的样式和布局,使其适合PDF格式。
<apex:page renderAs="pdf">
    <h1>PDF Report</h1>
    <p>Some report content here...</p>
</apex:page>

综上所述,通过掌握这些关于Apex和Visualforce代码编写的技巧,开发者能够编写出高质量、安全且易于维护的代码,提高开发效率,同时在应用部署和使用过程中避免许多潜在的问题。无论是在小型项目还是大型项目中,这些技巧都能发挥重要作用,帮助开发者更好地完成工作。

下面是一个简单的mermaid流程图,展示了从代码编写到部署的基本流程:

graph LR
    A[编写Apex和VF代码] --> B[代码审查]
    B --> C[测试]
    C --> D[修复问题]
    D --> E{是否通过测试}
    E -- 是 --> F[部署到生产环境]
    E -- 否 --> A

同时,为了更清晰地展示不同代码编写技巧的适用场景,我们可以列出以下表格:
| 技巧 | 适用场景 |
| ---- | ---- |
| 重用平台原生外观和感觉 | 创建面向Salesforce现有客户的页面 |
| 重用VF代码 | 中型和大型项目,多个开发者参与开发 |
| 限制视图状态 | 页面性能优化,减少数据传输 |
| 通过字段集编写灵活页面 | 需要动态显示字段的页面 |
| 加速AJAX调用 | 页面交互频繁,需要快速响应的场景 |
| 充分利用全局变量 | 简化代码,提高开发效率 |
| 避免JavaScript远程调用的常见错误 | 使用JavaScript Remoting技术的页面 |
| 注意Visualforce页面的安全性 | 涉及用户数据和敏感操作的页面 |
| 杂项技巧(图表、动态组件、PDF渲染) | 需要展示数据图表、动态内容或生成PDF报告的页面 |

【电能质量扰动】基于ML和DWT的电能质量扰动分类方法研究(Matlab实现)内容概要:本文研究了一种基于机器学习(ML)和离散小波变换(DWT)的电能质量扰动分类方法,并提供了Matlab实现方案。首先利用DWT对电能质量信号进行多尺度分解,提取信号的时频域特征,有效捕捉电压暂降、暂升、中断、谐波、闪变等常见扰动的关键信息;随后结合机器学习分类器(如SVM、BP神经网络等)对提取的特征进行训练分类,实现对不同类型扰动的自动识别准确区分。该方法充分发挥DWT在信号去噪特征提取方面的优势,结合ML强大的模式识别能力,提升了分类精度鲁棒性,具有较强的实用价值。; 适合人群:电气工程、自动化、电力系统及其自动化等相关专业的研究生、科研人员及从事电能质量监测分析的工程技术人员;具备一定的信号处理基础和Matlab编程能力者更佳。; 使用场景及目标:①应用于智能电网中的电能质量在线监测系统,实现扰动类型的自动识别;②作为高校或科研机构在信号处理、模式识别、电力系统分析等课程的教学案例或科研实验平台;③目标是提高电能质量扰动分类的准确性效率,为后续的电能治理设备保护提供决策依据。; 阅读建议:建议读者结合Matlab代码深入理解DWT的实现过程特征提取步骤,重点关注小波基选择、分解层数设定及特征向量构造对分类性能的影响,并尝试对比不同机器学习模型的分类效果,以全面掌握该方法的核心技术要点。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符  | 博主筛选后可见
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值