`

方法的实现方法,功能的实现方法。

 
阅读更多

方法的实现方法,功能的实现方法。使用算法。

1.什么是算法:方法的实现方法,问题的程序式解决方法。

算法的5个特征:

输入性:0个或多个输入。

输出性:1个或多个输出。

有穷性:方法必须在有穷的时间内执行完。

确定性:方法的每个语句都有确切的含义,不能有二义性。必须是相同的输入,有相同的输出。

可行性:方法的每一句都可以用计算机来执行。

 --

 

2.算法模式:

递归:自身调用自身。实现时要有结束条件。

归纳:尾递归。

例如:选择排序
对数组a1...an排序。
定i位的值
fun(0)
fun(i){
    if(i<n){
	    k=i;//k保存最小值的下标。
		for(j=i;j<n;j++){
			if(a[k]>a[j]){
				k=j;
			}
		}
		a[i]与a[j]交换位置;
		fun(i+1);
	}
}

 

分治:大规模划分成小规模分别解决,然后在组合起来。

二分法查找
在数组a1。。。an从小到大已排序中找k。
fun(low,high,k,a){
	mid=(low+high)/2; //向下取整。
	if(k==a[mid]) {
	    return mid;
	}else if(k<a[mid]){
		return fun(low,mid-1,k);
	}else{
	    return fun(mid+1,high,k);
	}
}

 

动态规划:解本问题解过程中会缓存和使用中间过程值。

求字符串A和B的最长公共子串的长度。
L[i,j]
A或B有一个串长度为0:L[i,j]=0;
ai是A最后一个,bj是B的最后一个,ai=bj:L[i,j]=L[i-1,j-1]+1;
ai!=bj:L[i,j]=min{L[i-1,j],L[i,j-1]};

//n为A的长度,m为B的长度。
fun(A,B){
	for(i=0;i<n:i++){
		L[i,0]=0;
	}
	for(j=0;j<m;j++){
		L[0,j]=0;
	}
	
	for(i=0;i<n;i++){
		for(j=0;j<m;j++){
			if(ai=bj){
			    return L[i-1,j-1]+1;//return fun(A.sub(i),B.sub(j));
			}else{
			    return min{L[i-1,j],L[i,j-1]}
			}
		}
	}
	
	return L[n,m];
}

 --

 

3.方法性能估算方法:

性能就是资源的使用情况:时间方面(时间复杂度),内存方面(空间复杂度),其他资源方面。

高性能就是:少时间,少内存,少其他资源。

时间方面的估算方法:

常见时间复杂度比较:

Ο(n!)>Ο(2的n次方)>Ο(n2)>Ο(nlog2n)>Ο(n)>Ο(log2n)>Ο(1)

1.基本步奏的执行次数。(有时是几个基本步骤的和)(一般次数是规模n的函数,在式子中找出使次数增长最快的项就是此算法的时间复杂度)

以下分析都是求最坏情况下的时间复杂度。 

 

归纳法的:选择排序的:时间复杂度:

基本步骤是:a[k]>a[j]

n=1:a[k]>a[j]执行1次

n=n:a[k]>a[j]执行比较次数是c(n)=c(n-1)+(n-1)次

式子展开得出:

c(n)=n(n-1)/2=1/2n的平方-1/2n;

所以时间复杂度是O(n的平法),读作O n的平方。

 

分治法的:二分法查找的:时间复杂度:

基本步骤是:三次比较中每次都会比较其中一个。

n=1:1

n>=2:c(n)=1+c(n/2向下取整)

式子展开:

c(n)<logn(向下取整)+1

所以时间复杂度是O(logn)

 

动态规划的:求字符串A和B的最长公共子串的长度的:时间复杂度:

基本步骤是:每次return L[i-1,j-1]+1或return min{L[i-1,j],L[i,j-1]}会执行一个。

n,m时:执行次数是c(n,m)=n*m

所以时间复杂度是O(nm)

 

2.具体执行时间测量。例如:可以在函数开始时打个时间戳,结束时打个时间戳,求执行时间。

 

内存方面的估算方法:

1.基本步奏需要的辅助内存。

--

 

4.方法的可读性:

1.程序书写要规范,注意缩进、空行。

2.需要必要的合理的注释。函数功能注释,关键步奏注释。

3.起有自身功能描述的函数名,或变量名。

4.方法功能单一,低耦合,高内聚。

5.其他面向对象设计原则。

---------------------------------------------------------------------------------------------------------------

1.排序

1.选择排序:每次选出最小值放到最首位,然后规模减1再次选出最小值,直到规模为0。

 

    void fun(int[] a, int len) {
        for (int i = 0; i < len; i++) {
            int minIndex = i;
            for (int j = i; j < len; j++) {
                if (a[minIndex] > a[j]) {
                    minIndex = j;
                }
            }

            if (minIndex != i) {
                int temp = a[i];
                a[i] = a[minIndex];
                a[minIndex] = temp;
            }
        }
    }
    //时间复杂度是:O(n的平方)
 

 

--

2.交换排序

1.冒泡排序:相邻两项比较,值大的放后位,然后位置+1再重复前面的步骤,一直到位置为length结束(这样达到了最大值在最后面)。规模-1再次前面的步骤,直到规模为0.

 

    void fun(int[] a) {
        for (int i = 0; i < a.length; i++) {
            for (int j = 0; j < a.length-i-1; j++) {
                if (a[j] > a[j+1]) {
                    int temp = a[j];
                    a[j] = a[j+1];
                    a[j+1] = temp;
                }
            }
        }
    }

//时间复杂度是:O(n的平方)
 2.快速排序:选择一个轴心值,小的放轴心值左边,大的放轴心值右边。以轴心位置为分界分成两部分,递归此过程。
void quicksort(int[] v, int left, int right) {
    if (left < right) {

        int pivotValue = v[left];
        int low = left;
        int high = right;
        while (low < high) {
            
            //从high开始一直找到比轴心值小的值放到low的位置
            // low位置的值不需要保存,值已经给pivotValue,(或high的位置,非循环第一次时))
            while (low < high && v[high] > pivotValue) {
                high--;
            }
            v[low] = v[high];
            
            //反转从low开始一直找到比轴心值大的的放到high的位置
            // (high位置的值不需要保存,值已经给low的位置)
            while (low < high && v[low] < pivotValue) {
                low++;
            }
            v[high] = v[low];
        }
        //现在low为轴心位置。
        v[low] = pivotValue;
        
        //以轴心位置分割两部分递归此过程。
        quicksort(v, left, low - 1);
        quicksort(v, low + 1, right);
    }
}
    
//时间复杂度是O(nlogn)

--

3.插入排序:i前的是有序的,把第i位的值插入到i前面的数组中。然后移动i的值,重复前面过程,直到i为数组长度。

 

public void insertSort(int a[]) {
    for (int i = 1; i < a.length; i++) {
        int insertIndex = i;
        int key = a[i];//当前要进行插入的值

        for (int j = i - 1; j >= 0; j--) {
            if (key < a[j]) {
                //后移元素
                a[j + 1] = a[j];
                insertIndex = j;
            } else {
                //大时在insertIndex的位置插入key
                break;
            }
        }
        a[insertIndex] = key;
    }
}

//时间复杂度是:O(n的平方)
 

 

--------------------------------------

2.查找

1.二分查找

 

int binary_search(int* a, int len, int goal)
{
    int low = 0;
    int high = len -1;
    while (low <= high)
    {
        int middle = (high - low) / 2 ;
        if (a[middle] == goal){
            return middle;
		}else if (a[middle] > goal){
            high = middle - 1;
		}else{
            low = middle + 1;
		}
    }
    return -1;
}
时间复杂度是:o(logn)

-------------------------------------

3.链表的逆序,插入,删除。

1.逆序:从头开始每个都提到最前面,q指向heap,p指向head的下一位。循环内先用q指向p的下一位,把p往前翻到head前,head再指向p。p向前移位。重复前面的步骤

Node reverse_Link(Node head) {
    Node p;
    Node q;
    q = head;
    p = head.next;
    while (p != null) {
        q.next = p.next;
        p.next = head;
        head = p;
        p = q.next;
    }
    return head;
}

 

 

2.插入:找到要插入的位置p,e.next=p.next,p.next=e;

//i位置前插入值e
insert_Link(Node head, int i, Node e) {
    Node p;
    p = head;

    for (int j = 1; j < i-1; j++) {
        if (p == null) {
            return;
        }
        p = p.next;
    }

    e.next = p.next;
    p.next = e;
}

 

 

3.删除:找到要删除的位置p,要删除的前一个位置p。q.next=p.next;

//删除位置i
delete_Link(Node head, int i){
    Node p;
    q = head;
    p = head;
    for (int j = 1; j < i; j++) {
        if (p == null) {
            return;
        }
        q = p;
        p = p.next;
    }

    if (p == null) {
        return;
    }

    if (p == q) {
        head = null;
    }

    q.next = p.next;
}

 

 

-------------------------------------

4.二叉树遍历与二叉树深度

二叉树遍历:

 

二叉树遍历:
前序遍历 根左右
void preOrder(BinaryTree bt) {
    if (pRoot != NULL) {
        visit(bt);//visit只是代表处理,关键的是结构
        preOrder(bt.leftChild);
        preOrder(bt.rightChild);
    }
}

中序遍历 左根右
void inOrder(BinaryTree bt) {
    if (pRoot != NULL) {
        inOrder(bt.leftChild);
        visit(bt); //visit只是代表处理,关键的是结构
        inOrder(bt.rightChild);
    }
}

后序遍历,左右根
void postOrder(BinaryTree bt) {
    if (bt != null) {
        postOrder(bt.leftChild);
        postOrder(bt.rightChild);
        visit(bt);//visit只是代表处理,关键的是结构
    }
}
 
二叉树深度
 
int treeDeep(BinaryTree bt) {
    int deep = 0;
    if (bt == null) {
        return 0;
    } else {
        int lChilddeep = treeDeep(bt.lChild);
        int rChilddeep = treeDeep(bt.rChild);
        deep = lChilddeep >= rChilddeep ? lChilddeep + 1 : rChilddeep + 1;
    }
    return deep;
}
 
  • 大小: 19.8 KB
  • 大小: 11.7 KB
  • 大小: 7.2 KB
分享到:
评论

相关推荐

    一种基于Android系统电视多功能单键操控的实现方法.pdf

    一种基于Android系统电视多功能单键操控的实现方法 Android系统电视多功能单键操控是电视行业发展的必然趋势。随着电视机产业的高速发展,对电视用户体验度的要求日益提高。传统的电视机按键板是物理机械式,但它...

    数值方法和matlab实现与应用 PDF

    《数值方法和MATLAB实现与应用》是一本深入探讨数值计算技术及其在MATLAB环境中的实际应用的专业书籍。这本书旨在帮助读者理解并掌握各种数值计算方法,并通过MATLAB这一强大的科学计算工具进行实践操作。 首先,...

    c#实现telnet功能

    本文将深入探讨如何使用C#编程语言实现telnet功能,并结合提供的文件名称"ScriptingTelnet"来解析其可能包含的实现方式。 C#是一种强大的面向对象的编程语言,广泛应用于Windows应用程序开发,Web服务,游戏开发等...

    基于BP和RBF方法实现uci葡萄酒数据集识别分类matlab实现源码+数据集.zip

    基于BP和RBF方法实现uci葡萄酒数据集识别分类matlab实现源码+数据集.zip基于BP和RBF方法实现uci葡萄酒数据集识别分类matlab实现源码+数据集.zip基于BP和RBF方法实现uci葡萄酒数据集识别分类matlab实现源码+数据集....

    c#实现录屏功能

    在C#编程环境中,实现录屏功能是一项常见的需求,尤其在开发桌面应用或者进行远程协助软件时。本项目通过利用Interop.WMEncoderLib.dll库,实现了C#中的录屏功能。WMEncoderLib.dll是Windows Media Encoder的COM接口...

    EDB MDB INI XML 同一功能的四种方法实现.rar

    EDB MDB INI XML 同一功能的四种方法实现.rar EDB MDB INI XML 同一功能的四种方法实现.rar EDB MDB INI XML 同一功能的四种方法实现.rar EDB MDB INI XML 同一功能的四种方法实现.rar EDB MDB INI XML 同一功能...

    Python开发Django 框架实现功能08. 用 Post 方法实现 django 表单.mp4

    Python开发Django 框架实现功能08. 用 Post 方法实现 django 表单.mp4

    C语言的Modbus RTU程序各种实现方法

    C语言的Modbus RTU程序各种实现方法,常见的集中方法及分析

    Asp.net Core 3.1基于AspectCore实现AOP实现事务、缓存拦截器功能

    最近想给我的框架加一种功能,就是比如给一个方法加一个事务的特性Attribute,那这个方法就会启用事务处理。给一个方法加一个缓存特性,那这个方法就会进行缓存。 这个也是网上说的面向切面编程AOP。 AOP的概念也很...

    (原创)modbus 协议c实现 C 语言 实现功能1 2 3 4 5 6 15 16

    本篇文章将详细探讨MODBUS协议的基本概念,C语言实现的关键点,以及如何在C语言中实现MODBUS协议的功能1至功能16。 1. MODBUS协议简介: MODBUS协议是一种通用的、公开的串行通信协议,由MODICON公司(现施耐德...

    常微分方程初值问题的欧拉方法及其改进的欧拉方法的Matlab实现

    常微分方程初值问题的欧拉方法及其改进的欧拉方法的Matlab实现,纪秀浩,,欧拉(Euler)方法及改进的欧拉方法是解决常微分方程初值问题常用的数值解法,但Matlab的工具箱中没有Euler方法的功能函数。本文在简要介

    C#实现打印机功能实例

    通过创建`PrintDocument`,设置`PrinterSettings`,重写`PrintPage`事件处理方法,可以轻松地实现预览和打印功能。对于更复杂的需求,可以深入研究`PrintController`和`PageSettings`,或者结合其他技术如GDI+来扩展...

    采用FFT方法实现数字接收多波束

    采用FFT方法实现雷达数字接收多波束功能,绘制N个接收波束的方向图。

    Qt 之 实现简单截图功能(一)

    我们通常会包含`#include &lt;QApplication&gt;`,`#include &lt;QGraphicsView&gt;`,`#include &lt;QGraphicsScene&gt;`,`#include &lt;QPixmap&gt;`和`#include &lt;QImageReader&gt;`等,这些头文件包含了实现截图功能所需的基本类和方法。...

    c#实现http post方法实例

    这里我们将重点讨论使用HttpClient的实现方式,因为它是.NET Framework 4.5及更高版本推荐的方法,具有更好的性能和易用性。 1. **HttpClient类的使用**: - 首先,需要引入命名空间`System.Net.Http`。 - 创建一...

    实现在asp.net中调用打印功能

    ASP.NET 调用打印功能实现方法 在 ASP.NET 中调用打印功能是一个常见的需求,特别是在报表生成和文档打印等场景中。下面我们将详细介绍如何在 ASP.NET 中实现打印功能。 标题解释 标题 "实现在 asp.net 中调用打印...

    实现类似网易邮箱的标签页功能

    实现类似网易邮箱的TAB标签页功能,很多管理软件也在用,仅供参考

    Android自定义Camera实现拍照功能

    要实现拍照功能,我们需要在CameraSurfaceView类中添加一个takePicture方法,该方法将调用Camera的takePicture方法来拍摄照片。同时,我们还需要提供三个回调函数:ShutterCallback、RawPictureCallback和...

    机器人操作系统ROS典型功能实现方法详解.docx

    .机器人操作系统ROS典型功能实现方法详解.docx

    机器人操作系统ROS典型功能实现方法详解.pdf

    .机器人操作系统ROS典型功能实现方法详解.pdf

Global site tag (gtag.js) - Google Analytics