[Java基本语法] 继承与多态

🌸个人主页:https://blog.csdn.net/2301_80050796?spm=1000.2115.3001.5343
🏵️热门专栏:🍕 Collection与数据结构 (92平均质量分)https://blog.csdn.net/2301_80050796/category_12621348.html?spm=1001.2014.3001.5482
🧀线程与网络(96平均质量分) https://blog.csdn.net/2301_80050796/category_12643370.html?spm=1001.2014.3001.5482
🍭MySql数据库(93平均质量分)https://blog.csdn.net/2301_80050796/category_12629890.html?spm=1001.2014.3001.5482
🍬算法(97平均质量分)https://blog.csdn.net/2301_80050796/category_12676091.html?spm=1001.2014.3001.5482
感谢点赞与关注~~~
在这里插入图片描述

目录

  • 1. 继承与多态
    • 1.1 继承
      • 1.1.1 为什么需要继承
      • 1.1.2 继承的概念
      • 1.1.3 继承的语法格式
      • 1.1.4 父类成员访问
        • 1.1.4.1子类中访问父类的成员变量
        • 1.1.4.2 子类中访问父类的成员方法
      • 1.1.5 super关键字
      • 1.1.6 子类构造方法
      • 1.1.7 super和this
      • 1.1.8 继承体系下的代码块
      • 1.1.9 再谈访问限定符
      • 1.1.10 继承方式
      • 1.1.11 final关键字
      • 1.1.12 继承与组合
    • 1.2 多态
      • 1.2.1 多态的概念
      • 1.2.2 多态实现的条件
      • 1.2.3 重写
      • 1.2.4 向上转型和向下转型
      • 1.2.5 避免在构造方法中使用重写的方法

1. 继承与多态

1.1 继承

1.1.1 为什么需要继承

Java中使用类对现实中的事物进行描述的时候,由于世间事物错综复杂,事物之间难免会存在一些特定的关联,这就是程序设计时候所需要考虑的问题。
比如:猫和狗都是动物
在这里插入图片描述
在这里插入图片描述我们使用Java语言就会有如下描述

public class Dog{string name;int age;float weight;public void eat(){System.out.println(name + "正在吃饭");}
public void sleep(){System.out.println(name + "正在睡觉");}
void Bark(){System.out.println(name + "汪汪汪~~~");}
}
public class Cat{string name;int age;float weight;public void eat(){System.out.println(name + "正在吃饭");}public void sleep(){System.out.println(name + "正在睡觉");}void mew(){System.out.println(name + "喵喵喵~~~");}
}

在这里插入图片描述

通过上述代码发现,猫类和狗类中有大量重复的成员,它们都有自己的名字,年龄,体重,它们都会吃,会睡觉,只有叫声是不一样的。那么我们能否对这写共性进行抽取呢?面向对象的程序设计思想中提出了继承的概念,专门用来进行共性抽取,以实现代码的复用

1.1.2 继承的概念

继承的机制:这是面向对象程序设计中使代码可以复用的最重要的手段,他允许程序员在保持一个类原有特征的同时进行扩展增加功能,这样产生的类,称为派生类。很好地体现了面向对象程序设计的清晰的层次结构。总之,继承所解决的问题就是:共性的抽取,实现代码的复用
在这里插入图片描述
如上图所示,Dog和Cat类都继承了Animal类,其中Animal类称为父类,基类,或者超类,Dog和Cat类称为子类或者派生类,继承之后,子类就可以复用父类中的成员,子类在实现时只关心自己的成员即可。

1.1.3 继承的语法格式

在Java中入如果要表示继承关系,需要使用extends关键字,具体格式如下:

修饰符 class 子类 extends 父类{
//
}

现在,我们使用继承语法对猫类和狗类进行重新设计:

public class Animal{String name;int age;public void eat(){System.out.println(name + "正在吃饭");}public void sleep(){System.out.println(name + "正在睡觉");}
}
public class Dog extends Animal{void bark(){System.out.println(name + "汪汪汪~~~");}
}
public class Cat extends Animal{void mew(){System.out.println(name + "喵喵喵~~~");}
}

注意事项

  • 子类会将父类的成员变量成员方法继承到子类中
  • 子类继承父类之后,必须要新添加自己特有的成员,否则就没必要继承了
  • static修饰的成员不可以继承,因为他们不属于对象,他们属于类(这时候可以返回上一篇文章看看删掉的那一行了)

1.1.4 父类成员访问

在继承体系中,既然子类把父类的方法和字段都继承下来了,那子类怎样去访问父类中的成员呢?

1.1.4.1子类中访问父类的成员变量
  1. 子类和父类不存在同名的情况
public class Base {int a;int b;
}
public class Derived extends Base{int c;public void method(){a = 10; // 访问从父类中继承下来的ab = 20; // 访问从父类中继承下来的bc = 30; // 访问子类自己的c}
}

不同名的情况下,可直接访问父类成员

  1. 子类和父类同名的情况
public class Base {int a;int b;int c;
}
public class Derived extends Base{int a; // 与父类中成员a同名,且类型相同char b; // 与父类中成员b同名,但类型不同public void method(){a = 100; // 访问父类继承的a,还是子类自己新增的a?自己的b = 101; // 访问父类继承的b,还是子类自己新增的b? 自己的c = 102; // 子类没有c,访问的肯定是从父类继承下来的c}
}

子类中的成员访问遵循以下原则

  • 如果访问的成员变量中,子类里有,优先访问自己的成员变量
  • 如果访问的成员变量中,子类中没有,但父类中有,则访问父类继承下来的
  • 如果访问的成员变量子类和父类重名,优先访问自己的

成员变量的访问遵循就近访问原则,自己有优先用自己的,如果没有再从父类中去找

1.1.4.2 子类中访问父类的成员方法
  1. 成员方法不同名
public class Base {public void methodA(){System.out.println("Base中的methodA()");}
}
public class Derived extends Base{public void methodB(){System.out.println("Derived中的methodB()方法");}public void methodC(){methodB(); // 访问子类自己的methodB()methodA(); // 访问父类继承的methodA()}
}
  1. 成员方法同名
public class Base {public void methodA(){System.out.println("Base中的methodA()");}public void methodB(){System.out.println("Base中的methodB()");}
}
public class Derived extends Base{public void methodA(int a) {System.out.println("Derived中的method(int)方法");//重载}public void methodB(){System.out.println("Derived中的methodB()方法");}public void methodC(){methodA(); // 没有传参,访问父类中的methodA()methodA(20); // 传递int参数,访问子类中的methodA(int)methodB(); // 直接访问,则永远访问到的都是子类中的methodB(),基类的无法访问到}
}

总结

  • 通过子类对象访问父类与子类不同名的方法时,优先在子类中找,否则在父类中找
  • 通过子类对象访问父类与子类同名的方法时,若两种方法构成重载,根据调用参数的不同调用相应的方法,至于参数列表相同的情况,我们在后面解释到方法的重写的时候再详细解释

那么问题来了,如果在子类中,我偏要访问父类的成员呢?这时我们就需要引入下一个关键字。

1.1.5 super关键字

既然想要在子类中访问父类的成员,直接访问是无法做到的,这时,Java就为我们提供了super关键字,这个关键字的作用是:在子类方法中访问父类成员

public class Base {int a;int b;public void methodA(){System.out.println("Base中的methodA()");}public void methodB(){System.out.println("Base中的methodB()");}
}
public class Derived extends Base{int a; // 与父类中成员变量同名且类型相同char b; // 与父类中成员变量同名但类型不同// 与父类中methodA()构成重载public void methodA(int a) {System.out.println("Derived中的method()方法");}// 与基类中methodB()构成重写(即原型一致,重写后序详细介绍)public void methodB(){System.out.println("Derived中的methodB()方法");}public void methodC(){// 对于同名的成员变量,直接访问时,访问的都是子类的a = 100; // 等价于: this.a = 100;b = 101; // 等价于: this.b = 101;// 注意:this是当前对象的引用// 访问父类的成员变量时,需要借助super关键字// super是获取到子类对象中从基类继承下来的部分super.a = 200;super.b = 201;// 父类和子类中构成重载的方法,直接可以通过参数列表区分清访问父类还是子类方法methodA(); // 没有传参,访问父类中的methodA()methodA(20); // 传递int参数,访问子类中的methodA(int)// 如果在子类中要访问重写的基类方法,则需要借助super关键字methodB(); // 直接访问,则永远访问到的都是子类中的methodA(),基类的无法访问到super.methodB(); // 访问基类的methodB()}}

注意事项

  • 只能在非静态方法中使用
  • 在子类方法中,访问父类的成员变量和方法会用到
  • super还有其他用法,后续介绍

1.1.6 子类构造方法

父子父子,先有父再有子,即:子类对象构造时,需要先调用父类的构造方法,然后再执行子类的构造方法

public class Base {public Base(){System.out.println("Base()");}
}
public class Derived extends Base{public Derived(){// super(); // 注意子类构造方法中默认会调用基类的无参构造方法:super(),// 用户没有写时,编译器会自动添加,而且super()必须是子类构造方法中第一条语句,// 并且只能出现一次System.out.println("Derived()");}
}
public class Test {public static void main(String[] args) {Derived d = new Derived();}
}

在子类的构造方法中,并没有写任何关于父类的构造代码,但是在构造子类对象时,先执行了父类的构造方法,然后执行子类的构造方法,因为:子类对象中成员是有两部分组成的,基类继承下来的以及子类新增加的部分 。先有父再有子所以在构造子类对象时候 ,先要调用基类的构造方法,将从基类继承下来的成员构造完整,然后再调用子类自己的构造方法,将子类自己新增加的成员初始化完整
注意

  • 如果父类,显式定义无参或者默认构造方法时,在子类构造方法的第一行有默认的super()调用,即调用父类的构造方法
  • 如果父类的构造方法是带有参数的,此时需要在子类构造方法中主动调用父类构造方法
  • 在子类构造方法中,super调用父类构造方法的语句必须放在子类构造方法的第一行
  • super只能在子类构造方法中出现一次,且不可以与this同时出现

1.1.7 super和this

【相同点】

  • 都是Java语言中的关键字
  • 只能在非静态方法中使用,用来访问非静态成员方法和字段
  • 在构造方法中调用时,必须是构造方法中的第一条语句,而且不能同时存在

【不同点】

  • this是指当前对象的引用,super相当于是子类对象从父类继承下来部分成员的引用
  • 在非静态成员方法中,this用来访问本类的方法和属性,super用来访问父类继承下来的方法和属性
  • 在构造方法中,==this调用本类的构造方法,super调用父类的构造方法,==但是两种方法不可以同时出现
  • 构造方法中一定会存在super调用,用户不写编译器会默认增加,但是this不写则没有

1.1.8 继承体系下的代码块

还记得我们之前讲的代码块吗,我们简单回顾,主要有两种代码块实例代码块和静态代码块,在没有继承关系下的执行顺序是:静态代码块>实例代码块

class Person {public String name;public int age;public Person(String name, int age) {this.name = name;this.age = age;System.out.println("构造方法执行");}{System.out.println("实例代码块执行");}static {System.out.println("静态代码块执行");}
}
public class TestDemo {public static void main(String[] args) {Person person1 = new Person("zhangsan",10);System.out.println("============================");Person person2 = new Person("lisi",20);}
}
  • 静态代码块先执行,并且只执行一次,在类加载阶段执行
  • 有对象创建时,才会执行实例代码块,实例代码块执行完成后,最后执行构造方法
    (详细内容请参考前面的文章)

要是加入了继承关系呢?

class Person {public String name;public int age;public Person(String name, int age) {this.name = name;this.age = age;System.out.println("Person:构造方法执行");}{System.out.println("Person:实例代码块执行");}static {System.out.println("Person:静态代码块执行");}
}
class Student extends Person{public Student(String name,int age) {super(name,age);System.out.println("Student:构造方法执行");}{System.out.println("Student:实例代码块执行");}static {System.out.println("Student:静态代码块执行");}
}
public class TestDemo4 {public static void main(String[] args) {Student student1 = new Student("zhangsan",19);System.out.println("===========================");Student student2 = new Student("lisi",20);}
}

执行结果:
Person:静态代码块执行
Student:静态代码块执行
Person:实例代码块执行
Person:构造方法执行
Student:实例代码块执行
Student:构造方法执行
===========================
Person:实例代码块执行
Person:构造方法执行
Student:实例代码块执行
Student:构造方法执行

经过上述分析,我们可以得出以下结论:

  • 父类静态>子类静态>父类实例>父类构造>子类实例>子类构造,原理就是,在java文件被写好之后,类就已经存在了,所以不管是父类还是子类,静态代码块都会被优先执行,且父类优先于子类,在之后实例化子类对象的时候,由于子类继承于父类,所以父类的实例代码块和构造方法优先被加载,创建一个对象的时候,先为对象分配内存空间,于是实例代码块被执行,之后调用构造方法,构造方法被执行,之后就是子类的实例代码块和构造方法
  • 第二次实例化的时候,父类和子类的静态代码块都不会再被执行,他们只执行一次,这是因为类只加载一次.

1.1.9 再谈访问限定符

再封装的章节,我们引入了访问限定符,主要限定:类或者类中成员能否再类外或者其他包中被访问

NO范围privatedefaultprotectedpublic
1同一包中的同一类
2同一包中的不同类×
3不同包中的子类××
4不同包中的非子类×××

这里记忆的时候,分为同一包和不同包,同一类和不同类,子类和非子类.

那么父类中不同访问权限的成员,在子类中的可见性怎么样呢?

// extend01包中
public class B {private int a;protected int b;public int c;int d;
}
// extend01包中
// 同一个包中的子类
public class D extends B{public void method(){// super.a = 10; // 编译报错,父类private成员在相同包子类中不可见super.b = 20; // 父类中protected成员在相同包子类中可以直接访问super.c = 30; // 父类中public成员在相同包子类中可以直接访问super.d = 40; // 父类中默认访问权限修饰的成员在相同包子类中可以直接访问}
}
// extend02包中
// 不同包中的子类
public class C extends B {public void method(){// super.a = 10; // 编译报错,父类中private成员在不同包子类中不可见super.b = 20; // 父类中protected修饰的成员在不同包子类中可以直接访问super.c = 30; // 父类中public修饰的成员在不同包子类中可以直接访问//super.d = 40; // 父类中默认访问权限修饰的成员在不同包子类中不能直接访问}
}
// extend02包中
// 不同包中的类
public class TestC {public static void main(String[] args) {C c = new C();c.method();// System.out.println(c.a); // 编译报错,父类中private成员在不同包其他类中不可见// System.out.println(c.b); // 父类中protected成员在不同包其他类中不能直接访问System.out.println(c.c); // 父类中public成员在不同包其他类中可以直接访问// System.out.println(c.d); // 父类中默认访问权限修饰的成员在不同包其他类中不能直接访问}
}
  • 如上面的代码所示,想要在子类中访问到父类中的成员,在允许访问到的前提下,我们可以通过super访问到
  • 父类中的private成员虽然在子类中不可以访问到,但是也继承到了子类中
  • 注意在使用访问限定符时,要认证思考,不可以滥用访问限定符,考虑好类中的字段和方法提供给“谁”用,从而加上合适的访问限定符

1.1.10 继承方式

在Java中只支持以下几种继承方式
在这里插入图片描述
注意Java中不支持多继承
就像一个孩子不可以有多个父亲一样,但是一个父亲可以有多个孩子,就像上面的第三种

1.1.11 final关键字

我们有时不希望一个类被继承,我们希望在继承上进行限制,这时我们就需要用到final关键字
,而且final不仅可以修饰类,还可以用来修饰变量,成员方法

  1. 修饰变量或者字段,表示常量(即不可以被修改)
final int a=10;
//a=20 error
  1. 修饰类,表示一个类不可以被继承,称为密封类
final public class Animal{
//
}
//public class Cat extends Animal{
//
//} error
  1. 修饰方法:表示该方法不可以被重写

1.1.12 继承与组合

和继承类似,组合也是一种表达类之间关系的方式,也可以实现代码的复用。组合并没有用到什么关键字,也没有固定的语法格式,仅仅是将一个类的实例作为另外一个类的字段
继承表示的是一种is a的关系,比如猫是动物
而组合表示的是一种has a的关系,比如人有心脏
在这里插入图片描述

class Heart{
//
}
class Brain{
//
}
class Lungs{
//
}
class Person{private Heart heart;private Brain brain;private Lungs lungs;
}

组合和继承都可以实现代码的复用,该继承还是组合,一般看实际的应用场景

1.2 多态

1.2.1 多态的概念

通俗来说就是:多种形态,具体一点就是去完成某个行为,当不同的对象去完成的时候会产生出不同的效果
在这里插入图片描述
总的来说:同一件事情发生在不同对象的身上,就会产生不同的结果

1.2.2 多态实现的条件

Java中想要实现多态,必须要满足以下几个条件,缺一不可:

  • 必须在继承体系下
  • 子类必须要对父类中的方法进行重写
  • 通过父类引用调用重写的方法
    多态实现:在代码运行时,当传递不同类对象时,会调用对应类中的方法
public class Animal {String name;int age;public Animal(String name, int age){this.name = name;this.age = age;}public void eat(){System.out.println(name + "吃饭");}
}
public class Cat extends Animal{public Cat(String name, int age){super(name, age);}
@Overridepublic void eat(){System.out.println(name+"吃鱼~~~");}
}
public class Dog extends Animal {public Dog(String name, int age){super(name, age);}@Overridepublic void eat(){System.out.println(name+"吃骨头~~~");}
}
public class TestAnimal {// 编译器在编译代码时,并不知道要调用Dog 还是 Cat 中eat的方法// 等程序运行起来后,形参a引用的具体对象确定后,才知道调用那个方法// 注意:此处的形参类型必须时父类类型才可以public static void eat(Animal a){a.eat();}public static void main(String[] args) {Cat cat = new Cat("元宝",2);Dog dog = new Dog("小七", 1);eat(cat);eat(dog);}
}

当类的调用者在编写eat这个方法的时候,参数类型为Animal,此时在方法内部并不关注当前的a指向的是那个类型的实例,此时a这个引用调用eat方法可能会有多种不同的表现,这种行为称为多态

1.2.3 重写

  1. 概念
    重写:也称为覆盖。重写就是对非静态方法,非private修饰的方法,非final修饰的方法,非构造方法的实现过程进行重新编写返回值和形参都不能改变,即外壳不变,实现核心重写,好处就是子类可以在父类的基础上实现自己的方法,定义特定于自己的行为
  2. 规则
  • 子类在重写父类的方法时,一般情况下返回值和形参都不能改变
  • 被重写的方法返回值类型有时可以不同,但是他们必须具有父子关系
  • 访问权限不可以比父类中被重写的方法更低,例如:父类方法被public修饰,则子类方法中重写该方法就不能声明为private
  • 父类方法不可以被static,final,private修饰,也不可以是构造方法,否者不可以被重写
  • 重写的方法,编译器会用“@override”来注解,可以检查合法性
  1. 重写和重载的区别
区别点重写重载
参数列表一定不可以修改必须修改
返回类型一定不可以修改(除非有父子关系)可以修改
访问限定符一定不可以降低权限可以修改

在这里插入图片描述

  1. 静态绑定与动态绑定
  • 静态绑定:也称为前期绑定,在编译时根据用户传递的参数类型就可以知道调用哪个方法,典型代表为方法的重载
  • 动态绑定:也称为后期绑定,在编译时,不可以确定方法的行为,无法知道调用哪个方法,需要等程序运行时才可以确定。

1.2.4 向上转型和向下转型

  1. 向上转型
    1. 概念:创建一个子类对象,把他当做父类对象来使用,就是范围从小到大的转换
    2. 语法格式:==父类类型 对象名=new 子类类型()
Animal animal=new Cat("miaomiao",2);

我们就拿上面的代码来说明:
在这里插入图片描述
3. 使用场景
- 直接赋值
- 方法传参
- 方法返回

public class TestAnimal {
// 2. 方法传参:形参为父类型引用,可以接收任意子类的对象public static void eatFood(Animal a){a.eat();}
// 3. 作返回值:返回任意子类对象public static Animal buyAnimal(String var){if("狗".equals(var) ){return new Dog("狗狗",1);}else if("猫" .equals(var)){return new Cat("猫猫", 1);}else{return null;}
}
public static void main(String[] args) {Animal cat = new Cat("元宝",2); // 1. 直接赋值:子类对象赋值给父类对象Dog dog = new Dog("小七", 1);eatFood(cat);eatFood(dog);Animal animal = buyAnimal("狗");animal.eat();animal = buyAnimal("猫");animal.eat();}
}

通过上述的代码,我们不难发现向上转型的有限,他可以使得代码更加简单灵活,但是缺点也很明显,不可以调用子类特有的方法,怎么办呢,我们这里便引出了向下转型

  1. 向下转型
    将一个子类对象经过向上转型之后当做了父类的对象使用,无法再调用到子类的方法,但是我们有时候会想要调用子类特有的方法,此时:将父类引用再还原为子类对象即可,即向下转型

    1. 语法格式:子类类型 对象名=(子类类名)经过向上转型的父类对象
      从上述语法格式来看,其实就是强制类型转换
    2. 安全性问题
      向下转型存在不安全的问题,不同于向上转型,是安全的,比如原来一个对象是狗类,向上转为了动物类,再向下转型的时候必须转回狗类,不可以转为猫类
      在这里插入图片描述
    public class TestAnimal {public static void main(String[] args) {Cat cat = new Cat("元宝",2);Dog dog = new Dog("小七", 1);// 向上转型Animal animal = cat;animal.eat();animal = dog;animal.eat();// 编译失败,编译时编译器将animal当成Animal对象处理// 而Animal类中没有bark方法,因此编译失败// animal.bark();// 向上转型// 程序可以通过编程,但运行时抛出异常---因为:animal实际指向的是狗// 现在要强制还原为猫,无法正常还原,运行时抛出:ClassCastExceptioncat = (Cat)animal;cat.mew();// animal本来指向的就是狗,因此将animal还原为狗也是安全的dog = (Dog)animal;dog.bark();}
    }
    
    1. 解决方案
      使用instanceof判断一个对象所属于的类是否属于一个类的父类
    public class TestAnimal {public static void main(String[] args) {Cat cat = new Cat("元宝",2);Dog dog = new Dog("小七", 1);// 向上转型Animal animal = cat;animal.eat();animal = dog;animal.eat();if(animal instanceof Cat){cat = (Cat)animal;cat.mew();}if(animal instanceof Dog){dog = (Dog)animal;dog.bark();}
    }
    }
    

1.2.5 避免在构造方法中使用重写的方法

下面展示一段有坑的代码

class B {public B() {func();}public void func() {System.out.println("B.func()");}
}
class D extends B {private int num = 1;@Overridepublic void func() {System.out.println("D.func() " + num);}
}
public class Test {public static void main(String[] args) {D d = new D();}
}

运行结果:D.func() 0
难道结果不应该是1吗,我们下面解释为什么不是1

在构造D对象的同时,会调用B的构造方法,在子类构造的时候,先构造父类。B的构造方法调用了func方法,此时会触发动态绑定,会调用D中的func,此时D还没有触发构造方法,D自身还没有构造,此时num处于未初始化状态,值为0,所以输出为0.
所以我们在构造方法中调用重写方法时一定要注意,在自己编程是尽量避免这种行为

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/27546.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【LeetCode:2786. 访问数组中的位置使分数最大 + 递归 + 记忆化缓存 + dp】

🚀 算法题 🚀 🌲 算法刷题专栏 | 面试必备算法 | 面试高频算法 🍀 🌲 越难的东西,越要努力坚持,因为它具有很高的价值,算法就是这样✨ 🌲 作者简介:硕风和炜,…

家用RJ45水晶头可以用在工业互联网中?

工业互联网作为智能制造的核心组成部分,已经在工业领域快速发展。在建立连接不同设备和系统的复杂网络中,网络设备和连接器的选择变得至关重要。其中,普遍使用的RJ45水晶头和网线在家庭和小型商业网络中被广泛采用,但是否适用于工…

Flink作业执行之 3.StreamGraph

Flink任务如何跑起来之 3.StreamGraph 1. StreamGraphGenerator 在前文了解Transformation和StreamOperator后。接下来Transformation将转换成StreamGraph,即作业的逻辑拓扑结构。 在env.execute()方法中调用getStreamGraph方法生成StreamGraph实例。StreamGraph…

如何在 ASP.NET Core Web Api 项目中应用 NLog 写日志?

前言 昨天分享了在 .NET Core Console 项目中应用 NLog 写日志的详细例子,有几位小伙伴私信说 ASP.NET Core Web Api 项目中无法使用,其实在 ASP.NET Core Web Api 项目中应用 NLog 写日志,跟 .NET Core Console 项目是有些不一样的&#xf…

如何确保数据跨域交换安全、合规、可追溯性?

数据跨域交换是指在不同的组织、系统或网络之间进行数据的传输和共享。随着数字经济的发展,数据跨域交换在促进数据流通和创新融合方面发挥着重要作用。然而,这一过程也面临着诸多挑战和风险,例如数据安全、合规性、完整性以及责任不清晰等问…

顶顶通呼叫中心中间件(mod_cti基于FreeSWITCH)-通话时长限制

文章目录 前言联系我们场景运用机器人场景普通通话场景 前言 顶顶通呼叫中心中间件限制通话时长有两种写法,分别作用于机器人场景与普通通话场景。 普通场景可分为分机互打、分机外呼手机等。 联系我们 有意向了解呼叫中心中间件的用户,可以点击该链接…

SAP Build 2-PDF数据提取与决策

0. 安装desktop agent 在后续过程中发现要预先安装desktop agent,否则没法运行自动化流程… 0.1 agent下载 参考官方文档说明 https://help.sap.com/docs/build-process-automation/sap-build-process-automation/create-user-in-rbsc-download-repository?loca…

RabbitMQ安装配置,封装工具类,发送消息及监听

1. Get-Started docker安装rabbitmq 拉取镜像 [rootheima ~]# docker pull rabbitmq:3.8-management 3.8-management: Pulling from library/rabbitmq 7b1a6ab2e44d: Pull complete 37f453d83d8f: Pull complete e64e769bc4fd: Pull complete c288a913222f: Pull complet…

C# Winform Chart图表使用和详解

Chart控件是微软自带的一种图形可视化组件,能展示种类丰富的图表形式。如曲线图,折线图,饼状图,环形图,柱状图,曲线面积图。 实例代码链接:https://download.csdn.net/download/lvxingzhe3/8943…

【wiki知识库】06.文档管理接口的实现--SpringBoot后端部分

目录 一、🔥今日目标 二、🎈SpringBoot部分类的添加 1.调用MybatisGenerator 2.添加DocSaveParam 3.添加DocQueryVo 三、🚆后端新增接口 3.1添加DocController 3.1.1 /all/{ebokId} 3.1.2 /doc/save 3.1.3 /doc/delete/{idStr} …

[Qt] Qt Creator 以及 Qt 在线安装教程

一、Qt Creator 下载及安装 1、从以下镜像源下载安装包常规安装即可 Qt Creator 也可以在第二步Qt 在线安装时一次性勾选安装,见后文 Qt Creator 中科大源下载地址 二、Qt 在线安装 1、根据所在平台选择对应的安装器下载 Qt 在线安装器下载 2、可能的安装报错…

云电脑有多好用?适合哪些人使用?

云电脑作为一种新型的计算模式,其应用场景广泛且多样,适合各类人群使用。云电脑适合什么人群使用?云电脑有哪些应用场景?有什么好的云电脑推荐?以下本文将详细探讨云电脑的主要应用场景及其适用人群的相关内容&#xf…

禁用PS/Photoshop等一系列Adobe旗下软件联网外传用户数据操作

方案一: 下载火绒杀毒,在联网请求上禁用Adobe软件的联网请求,甚至还可以额外发现哪些是它要想要偷偷摸摸干的。 方案二: 最后注意: 用盗版软件只是获得了使用权!

Docker系列.Docker Desktop中如何启用Kubernetes

Docker技术概论 Docker Desktop中如何启用Kubernetes - 文章信息 - Author: 李俊才 (jcLee95) Visit me at CSDN: https://jclee95.blog.csdn.netMy WebSite:http://thispage.tech/Email: 291148484163.com. Shenzhen ChinaAddress of this article:https://blog.…

Linux编辑器 vim使用 (解决普通用户无法进行sudo提权问题)

文章目录 一.vim是什么命令模式底行模式 二.关于vim暂停问题三.注释批量化注释批量化去注释 四.解决普通用户无法进行sudo提权问题五.vim的配置 一.vim是什么 用过VS的都知道,拥有着编辑器编译器调试.编写C,C,python等的功能。就是集成 Linu…

LeetCode | 434.字符串中的单词数

这道题直接使用语言内置的 split 函数可直接分离出字符串中的每个单词,但是要注意区分两种情况:1、空串;2、多个空格连续,分割后会出现空字符的情况,应该舍弃 class Solution(object):def countSegments(self, s):&qu…

Dubbo3 服务原生支持 http 访问,兼具高性能与易用性

作者:刘军 作为一款 rpc 框架,Dubbo 的优势是后端服务的高性能的通信、面向接口的易用性,而它带来的弊端则是 rpc 接口的测试与前端流量接入成本较高,我们需要专门的工具或协议转换才能实现后端服务调用。这个现状在 Dubbo3 中得…

SVN 报错Error: Unable to connect to a repository at URL解决方法

1. 报错背景: 使用ssh 用svn拉取仓库代码时,出现如下报错: Can’t create session: Unable to connect to a repository at URL svn://127.0.0.1 …. Can’t connect to host ‘127.0.0.1’: Connection refused at C:/Program Files/Git/mi…

蓝牙耳机怎么连接电脑?轻松实现无线连接

蓝牙耳机已经成为许多人生活中不可或缺的一部分,不仅可以方便地连接手机,还能轻松连接电脑,让我们在工作和娱乐时享受无线的自由。然而,对于一些用户来说,将蓝牙耳机与电脑连接可能会遇到一些问题。本文将介绍蓝牙耳机…

从大型语言模型到大脑语言理解:探索话语理解的神经机制

随着科技的飞速发展,人工智能领域取得了令人瞩目的成就。在这其中,大型语言模型(LLMs)以其卓越的性能和广泛的应用前景,成为了当前研究的热点。然而,尽管LLMs在文本生成、语言翻译等领域展现出了惊人的能力…