精华内容
下载资源
问答
  • 如何在Kotlin中使用扩展函数和扩展属性发布时间:2021-05-16 11:10:55来源:亿速云阅读:56作者:Leah如何在Kotlin中使用扩展函数和扩展属性?很多新手对此不是很清楚,为了帮助大家解决这个难题,下面小编将为大家...

    如何在Kotlin中使用扩展函数和扩展属性

    发布时间:2021-05-16 11:10:55

    来源:亿速云

    阅读:56

    作者:Leah

    如何在Kotlin中使用扩展函数和扩展属性?很多新手对此不是很清楚,为了帮助大家解决这个难题,下面小编将为大家详细讲解,有这方面需求的人可以来学习下,希望你能有所收获。

    Kotlin 能够扩展一个类的新功能而无需继承该类或者使用像装饰者这样的设计模式。 这通过叫做 扩展 的特殊声明完成。 例如,你可以为一个你不能修改的、来自第三方库中的类编写一个新的函数。 这个新增的函数就像那个原始类本来就有的函数一样,可以用普通的方法调用。 这种机制称为 扩展函数 。public class Utils {

    public static float dp2px(int dpValue) {

    return (0.5f + dpValue * Resources.getSystem().getDisplayMetrics().density);

    }

    }

    在代码中直接调用 Utils.dp2px(100) 来使用,val dp2px = Utils.dp2px(100)

    如果用kotlin扩展函数的方式来实现,会是怎么调用呢?val dp2px = 100.dp2px()

    是不是很惊讶,100作为一个Int,竟然直接调用了一个dp2px方法,如果你去源码里找找,其实是没有个方法的。我们没有动源码,而是使用拓展函数的方式为Int增加了一个方法。fun Int.dp2px(): Float {

    return (0.5f + this * Resources.getSystem().displayMetrics.density)

    }

    扩展函数

    我们再来举个?,有一个Person类如下class Person(val name: String) {

    fun eat() {

    Log.i(name, "I'm going to eat")

    }

    fun sleep() {

    Log.i(name, "I'm going to sleep")

    }

    }

    它有两个方法,一个是 eat 、一个是 sleep,调用的话就分别打印相应的Log。我们现在不想动Person类,但是又想给他增加一个新的方法,怎么做呢。我们可以新建一个文件 PersonExtensions.kt,再通过一下代码实现,就可以为 Person类新增一个 drink 方法啦。fun Person.drink() {

    Log.i("Person", "${this.name}: I'm going to drink")

    }

    声明一个扩展函数,我们需要用一个 接收者类型 也就是被扩展的类型来作为他的前缀。上面我们就是以 Person 作为一个扩展函数的接收类型,为其拓展来 drink 方法。我们在其方法中调用了 this ,这个 this 指的就是调用这个拓展方法的当前 Person 对象。

    fa374cfdd94956d706e2cf86fdec79ba.png

    扩展函数调用的话也和普通的方法相同。但是你会发现IDE显示的方法颜色有点不一样。

    35c3dfb7190f5e7e1660624466885eba.png

    由此也可以看出普通的方法和我们的拓展函数是不同的。下面我们来看看扩展函数的实际实现。

    在 Android Studio 中,我们可以查看 kotlin 文件的字节码,然后再 Decompile 为 Java 代码。上面我们为 Person 扩展函数转为Java代码后如下。@Metadata(

    mv = {1, 1, 15},

    bv = {1, 0, 3},

    k = 2,

    d1 = {"\u0000\f\n\u0000\n\u0002\u0010\u0002\n\u0002\u0018\u0002\n\u0000\u001a\n\u0010\u0000\u001a\u00020\u0001*\u00020\u0002¨\u0006\u0003"},

    d2 = {"cook", "", "Lcom/chaochaowu/kotlinextension/Person;", "app_debug"}

    )

    public final class PersonExtensionsKt {

    public static final void cook(@NotNull Person $this$cook) {

    Intrinsics.checkParameterIsNotNull($this$cook, "$this$cook");

    Log.i("Person", $this$cook.getName() + ": I'm going to cook");

    }

    }

    妹想到啊,它原来是一个 static final 声明的静态方法,它的入参是一个 Person 类型,也就是我们之前的接收类型。那在Java代码中能不呢调用呢?PersonExtensionsKt.cook(new Person("Bob"));

    竟然也没有报错!由此可见,所谓扩展函数并不是真正的在类中增加了一个方法,而是通过外部文件的静态方法来实现,其实就是和Utils类一个道理。

    因为将一个 Person 作为入参传入了方法中,所以我们也就可以在方法内对这个 Person 对象进行操作,这也就是在扩展方法中我们可以使用 this 来访问 Person 属性的原因。

    再来看一个特殊的例子。val s: String? = null

    s.isNullOrEmpty()

    上面的代码中,s的值为null,我们用null去调用了一个方法,这会不会报错呢?按照以前的经验,一个null去调用一个方法,必然会报空指针的异常,但是上面的代码却是不会崩的。为什么哩?

    其实 isNullOrEmpty 是 CharSequence? 的一个扩展方法,我们可以看一下它的源码。@kotlin.internal.InlineOnly

    public inline fun CharSequence?.isNullOrEmpty(): Boolean {

    contract {

    returns(false) implies (this@isNullOrEmpty != null)

    }

    return this == null || this.length == 0

    }

    contract这个契约方法这边我们不需要注意,不影响。主要是看 return this == null || this.length == 0 这句话。它先是判断了 this 是否为空,然后再判断this 的长度。根据我们上面讲的扩展函数的本质,我们可以很好的理解,为什么null可以调用这个方法的原因。因为上面的代码转为 Java 代码后是这样子的。public static final boolean isNullOrEmpty(@Nullable CharSequence $this$isNullOrEmpty) {

    int $i$f$isNullOrEmpty = 0;

    return $this$isNullOrEmpty == null || $this$isNullOrEmpty.length() == 0;

    }

    我们在用null调用这个扩展方法时,其实是将null作为一个参数传入这个方法中,先判断参数是否为null,再进行下一步判断,这当然不会崩溃。

    扩展不能真正的修改他们所扩展的类。通过定义一个扩展,你并没有在一个类中插入新成员, 仅仅是可以通过该类型的变量用点表达式去调用这个新函数,并将自身作为参数传入。

    扩展属性

    扩展属性和扩展函数类似,再举上面Person 的例子,我们对 Person 类稍作修改,为其增加 birthdayYear 字段,表示其出生的年份。class Person(val name: String, val birthdayYear: Int) {

    fun eat() {

    Log.i(name, "I'm going to eat")

    }

    fun sleep() {

    Log.i(name, "I'm going to sleep")

    }

    }

    我们现在要为 Person 增加年龄 age 的属性,但是不改 Person 类,怎么实现呢。和扩展函数一样,在其他文件中声明如下。const val currentYear = 2019

    val Person.age: Int

    get() = currentYear - this.birthdayYear

    我们通过当前年份减去生日年份计算出 Person 的年龄。可以看到,age 是一个属性,而不是方法。这样我们就为 Person 增加了一个扩展属性。可以看看它转化为 Java 代码后的样子,和扩展函数没啥区别。@Metadata(

    mv = {1, 1, 15},

    bv = {1, 0, 3},

    k = 2,

    d1 = {"\u0000\u0010\n\u0000\n\u0002\u0010\b\n\u0000\n\u0002\u0018\u0002\n\u0002\b\u0003\"\u000e\u0010\u0000\u001a\u00020\u0001X\u0086T¢\u0006\u0002\n\u0000\"\u0015\u0010\u0002\u001a\u00020\u0001*\u00020\u00038F¢\u0006\u0006\u001a\u0004\b\u0004\u0010\u0005¨\u0006\u0006"},

    d2 = {"currentYear", "", "age", "Lcom/chaochaowu/kotlinextension/Person;", "getAge", "(Lcom/chaochaowu/kotlinextension/Person;)I", "app_debug"}

    )

    public final class PersonExtensionsKt {

    public static final int currentYear = 2019;

    public static final int getAge(@NotNull Person $this$age) {

    Intrinsics.checkParameterIsNotNull($this$age, "$this$age");

    return 2019 - $this$age.getBirthdayYear();

    }

    }

    看完上述内容是否对您有帮助呢?如果还想对相关知识有进一步的了解或阅读更多相关文章,请关注亿速云行业资讯频道,感谢您对亿速云的支持。

    展开全文
  • 1. 扩展函数的写法 // fun 关键字 + 要扩展的类名 + 点号 + 方法名 + 方法属性 fun String.method1(i: Int) { ... } 这里要扩展函数的类名叫做Receiver(接受者),也就是谁可以去调用它. 在声明一个函数的时候在...

    1. 扩展属性

    kotlin允许动态为类扩展属性,扩展属性是通过添加get、set方法实现,没有幕后字段(filed)。
    扩展属性也没有真的为该类添加了属性,只能说是为该类通过get、set方法计算出属性。
    限制:①扩展属性不能有初始值;
    ②扩展属性不能用filed关键字访问幕后字段;
    ③val必须提供get方法,var必须提供get和set方法。

    var类型
    
    	class ExtensionTest(var param1: String, var param2: String)
    	
    	var ExtensionTest.extensionParam: String
    	    set(value) {
    	        param1 = "param1$value"
    	        param1 = "param2$value"
    	    }
    	    get() = "$param1-$param2"
    	    
    	fun main(args: Array<String>) {
    	    val extensionTest = ExtensionTest("a", "b")
    	    println(extensionTest.param1)//a
    	    println(extensionTest.param2)//b
    	    println(extensionTest.extensionParam)//a-b
    	}
    
    
    val类型
    
    	val Float.dp
    	  get() = TypedValue.applyDimension(
    	    TypedValue.COMPLEX_UNIT_DIP,
    	    this,
    	    Resources.getSystem().displayMetrics
    	  )
    	...
    	val RADIUS = 200f.dp
    

    2. 扩展函数的写法

    // fun 关键字 + 要扩展的类名 + 点号 + 方法名 + 方法属性
    fun String.method1(i: Int) {
      ...
    }
    
    这里要扩展函数的类名叫做Receiver(接受者),也就是谁可以去调用它.

    在声明一个函数的时候在函数名的左边写个类名再加个点,你就能对这个类的对象调用这个函数了。这种函数就叫扩展函数,Extension Functions。就好像你钻到这个类的源码里,改了它的代码,给它增加了一个新的函数一样。虽然事实上不是,但用起来基本一样。

    注意:

    1. 如果被扩展的类的扩展方法与该类的成员方法名字和参数一样,该类对象调用该方法时,调用的会是成员方法。
    2. 由于静态调用扩展方法是在编译时执行,因此,如果父类和子类都扩展了同名的一个扩展方法,引用类型均为父类的情况下,会调用父类的扩展方法。

    3 Top Level扩展函数

    package com.zhf
    
    fun String.method1(i: Int) {
      ...
    }
    
    // 在使用的地方调用就可以了
    "rengwuxian".method1(1)
    
    Top Level扩展函数是属于谁呢?

    它既是Top Level函数,又是前缀类的扩展函数, 它的作用域是package包内部, 他的Receiver是点左侧的类

    看了很多教程和解释, 自己理解其实这个函数就是个顶层函数,它只属于它所在的 package, 不过他只能被Receiver(接收者)使用, 就是上面代码里的String,

    虽然说它是个 Top-level Function,不属于任何类——确切地说是,不是任何一个类的成员函数——但我要限制只有通过某个类的对象才能调用你。这就是扩展函数的本质。

    4 成员扩展函数

    写在类里的扩展函数 , 你可以在这个类里调用这个函数,但必须使用那个前缀类的对象(Receiver)来调用它

    class Example {
      fun String.method2(i: Int) {
        ...
      }
       "rengwuxian".method2(1) // 可以调用
    }
    
    成员扩展函数是属于谁呢? —

    它既是外部类的成员函数,又是前缀类的扩展函数. 它的作用域是类内部, 他的Receiver是点左侧的类

    这个「属于谁」其实有点模糊的,我需要问再明确点:
    它是谁的成员函数?当然是外部的类的成员函数了,因为它写在它里面嘛,
    那函数名左边的是什么?它是这个函数的 Receiver,对吧?也就是谁可以去调用它。
    所以它既是外部类的成员函数,又是前缀类的扩展函数。

    5 指向扩展函数的引用

    函数是可以使用双冒号被指向的, 双冒号加方法名 指向的并不是函数本身,而是和函数等价的一个对象,
    我们通常可以把这个「指向和函数等价的对象的引用」称作是「指向这个函数的引用」

    顶层扩展函数的 指向扩展函数的引用

    fun String.method1(i: Int) {
    }
    String::method1 
    

    上面 String::method1 就是指向扩展函数的引用, 它其实是可以作为对象来传递和使用的,当然它也可以作为参数,传递给方法, 这就是高阶函数了
    注意: 以下代码中 method3 和 method4 为什么都可以 传如String 的函数引用 下文会说到

    	fun String.method1(i: Int): String {
    	}
    	class Example {
    		val a = String::method1
    		val b = a
    
            method3(String::method1)
            method3(b)
            
            method4(String::method1)
            method4(b)
    
    		fun method3(method: String.(Int) -> String) {}
    		fun method4(method: (String, Int) -> String) {}
    	}
     
    

    成员扩展函数的 指向扩展函数的引用 ( *** 不存在)

    一个成员函数怎么引用:类名加双冒号加函数名对吧?扩展函数呢?也是类名加双冒号加函数名对吧?只不过这次是 Receiver 的类名。那成员扩展函数呢?还用类名加双冒号加函数名呗?但是……用谁的类名?是这个函数所属的类名,还是它的 Receiver 的类名?这是有歧义的,所以 Kotlin 就干脆不许我们引用既是成员函数又是扩展函数的函数了,一了百了。

    	fun Extensions .method2(i: Int) {
    		...
    	}
    	class Extensions {
    	  fun String.method1(i: Int) {
    	    ...
    	  }
    	  fun method2(i: Int) {
    		...
    	  }
    	  String::method1 // 报错
    	}
    	
    	class Example {
    		Extensions ::method1 // 报错
    		Extensions ::method2  // 方法名相同, 成员方法优先
    	}
    

    6 把扩展函数的引用赋值给变量

    扩展函数的引用也可以赋值给变量, 然后你再拿着这个变量去调用,或者再次传递给别的变量,都是可以的
    跟普通函数的引用一样,扩展函数的引用也可以被调用,直接调用或者用 invoke() 都可以,不过要记得把 Receiver 也就是接收者或者说调用者填成第一个参数

    	
    	val a: String.(Int) -> Unit = String::method1
    	"zhf".a(1)
    	a("zhf", 1)
    	a.invoke("zhf", 1)
    

    7 有无 Receiver 的变量的互换

    在 Kotlin 里,每一个有 Receiver 的函数——其实就是成员函数和扩展函数——它的引用都可以赋值给两种不同的函数类型变量:一种是有 Receiver 的,一种是没有 Receiver 的:
    有 Receiver 的函数和没有 Receiver 的函数,在写法上就是把 Receiver 放在没有Receiver 的第一个参数

    	val a: String.(Int) -> Unit = String::method1
    	val b: (String, Int) -> Unit = String::method1
    	
    	val c: String.(Int) -> Unit = b
    	val d: (String, Int) -> Unit = a
    

    扩展 (可直接跳过)

    下面三段代码,第一段代码里的 clz / clz1/ clz2/ clz3 这四个对象是一个对象吗? 他们之间有何不同呢?

    1. LoginActivity::class 和 mLoginActivity::class 这两个是相同的对象,
      类名或者类的对象加双冒号,代表 指向扩展函数的引用 所以 clz1和clz2 是相同的对象
    2. LoginActivity::class 返回的是什么呢 ? 在kotlin中的Class与Java不同,
      kotlin中有一个自己的Class叫做KClass 双冒号加class 返回的就是 KClass
    3. mLoginActivity::class.java 和 mLoginActivity.javaClass 这两个是相同的对象 .
      第二段代码,是KClass 的一个扩展函数, 他的返回值是 Class 第三段代码,是T 的一个扩展函数, T就是某个函数名 他的返回值是 Class

    结论就是: clz != clz1 == clz2 ==clz3

           代码一 
            val clz = LoginActivity::class
            val clz1 = LoginActivity::class.java
            val clz2 = mLoginActivity::class.java
            val clz3 = mLoginActivity.javaClass
      
            val intent = Intent();
            intent.setClass(mContext, clz1 )
            startActivity(intent)
    
    代码二
    	@Suppress("UPPER_BOUND_VIOLATED")
    	public val <T> KClass<T>.java: Class<T>
    	    @JvmName("getJavaClass")
    	    get() = (this as ClassBasedDeclarationContainer).jClass as Class<T>
    
    代码三
    	public inline val <T : Any> T.javaClass: Class<T>
    	    @Suppress("UsePropertyAccessSyntax")
    	    get() = (this as java.lang.Object).getClass() as Class<T>
    

    本文摘录自:
    https://rengwuxian.com/kotlin-extensions/
    https://www.cnblogs.com/nicolas2019/p/10932131.html

    展开全文
  • Flutter 扩展函数

    2021-04-20 16:57:19
    Extension methods 就是我们常说的扩展函数,像 Kotlin 等语言也有 扩展函数 的特性,因此如果你了解其他语言的扩展函数,Dart 中的扩展函数与其他语言基本一致。 扩展函数最低版本要求: environment: sdk: ">=...

    Extension methods 就是我们常说的扩展函数,像 Kotlin 等语言也有 扩展函数 的特性,因此如果你了解其他语言的扩展函数,Dart 中的扩展函数与其他语言基本一致。

    扩展函数最低版本要求:

    environment:
      sdk: ">=2.6.0 <3.0.0"
    

    注意:2.6.0版本需要在项目根目录新建一个名字为 analysis_options.yaml 的文件,文件里输入一下内容,2.6.0版本以上就不需要

    analyzer:
      enable-experiment:
        - extension-methods
    

    注意:空安全的最低版本是 2.12.0。

    基础

    那么什么是扩展函数?

    简单理解,扩展函数就是在现有的库或者类中扩展一个函数,比如,我们希望将一个整数字符串转换为 int 类型整数,正常情况下,实现如下:

    int.parse('10');
    

    但是此中写法不是很美观,比较美观的写法是这样的:

    '10'.toInt();
    

    但是 String 类型并没有 toInt 方法,这时扩展函数就有了用武之地,我们给 String 扩展一个 toInt 方法:

    extension StringExtension on String {
      int toInt() {
        return int.parse(this);
      }
    }
    
    • 扩展函数使用关键字 extension。
    • StringExtension:是扩展函数的名称。
    • on :关键字后接需要扩展的类型。
    • 大括号:内部是扩展的方法。

    有人觉得这个例子并不能体现 扩展函数 的强大之处,看下面这个例子,假设有一个第三方库的类 Person:

    class Person {
      final String name;
    
      Person(this.name);
    }
    

    有2个实例 person1 和 person2,我们希望这个2个实例相加,返回一个 Person 对象且name 值为2个name的拼接,中间用 , 隔开,不使用扩展函数实现:

    Person add(Person person1,Person person2){
        return Person('${person1.name},${person2.name}');
    }
    

    下面使用扩展函数实现:

    extension PersonExtension on Person {
      Person operator +(Person person) {
        return Person('${this.name},${person.name}');
      }
    }
    

    使用:

    Person person1 = Person('lao');
    Person person2 = Person('meng');
    Person p = add(person1, person2);
    print('${p.name}');
    Person p1 = person1 + person2;
    print('${p1.name}');
    

    输出结果:

    flutter: lao,meng
    flutter: lao,meng
    

    结果都是一样的,都可以实现要求,但扩展函数的可读性更好。

    注意:扩展函数可以实现的功能,使用工具类(方法)同样也可以实现。

    var 和 dynamic
    不能对 dynamic 类型使用扩展函数,下面的用户在运行时出现异常:

    dynamic a = '10';
    a.toInt();
    

    toInt 是 String 类型的扩展函数,运行出现如下异常:

    图片

    但是如下代码是正确的:

    var b = '10';
    b.toInt();
    

    因为 b 以及被推断为 String 类型,所以可以使用扩展函数。

    通过上面的例子,我们已经对扩展函数有了一定的了解,扩展函数除了可以扩展方法外,还可以扩展属性、操作符。

    class Person {
      String name;
    
      Person(this.name);
    }
    

    扩展函数:

    extension PersonExtension on Person {
      // 扩展操作符 +
      Person operator +(Person person) {
        return Person('${this.name},${person.name}');
      }
    
      // 扩展 getter 属性
      int get nameLength => this.name.length;
    
      //已经存在的方法不能扩展
      // String toString(){
      //   return 'name:${this.name},age:${this.age}';
      // }
      //扩展 方法
      String log() {
        return 'name:${this.name}';
      }
    }
    

    使用:

    Person person = Person('flutter');
    print('${person.nameLength}');
    print('${person.log()}');
    

    解决冲突
    假设现在有2个扩展函数,分别在 string_extension.dart 和 string_extension_1.dart 文件中,string_extension.dart 代码如下:

    extension StringExtension on String {
      int toInt() {
        return int.parse(this);
      }
    }
    

    string_extension_1.dart 代码如下:

    extension StringExtension1 on String {
      int toInt() {
        return int.parse(this);
      }
    
      double toDouble() {
        return double.parse(this);
      }
    }
    

    string_extension_1.dart 中的代码比 string_extension.dart 多了一个 toDouble 方法。

    引入2个扩展函数并使用 toInt 方法:

    import 'string_extension.dart';
    import 'string_extension1.dart';
    
    String a = '10';
    a.toInt();
    

    此时,无法编译通过,异常如下:

    图片

    异常原因:2个扩展函数中都有 toInt 方法。

    解决方案1: 指定使用哪一个扩展函数

    String a = '10';
    StringExtension(a).toInt();
    

    解决方案2: 使用 hide 和 show 来限制

    import 'string_extension.dart';
    import 'string_extension1.dart' hide StringExtension1;
    
    String a = '10';
    a.toInt();
    

    转载:老孟Flutter公众号,原文链接:https://mp.weixin.qq.com/s/uxHHsEupoIvcD2OUhQEi6w

    展开全文
  • 在Kotlin中,创建一个协程,需要调用createCoroutine函数,有两个函数叫这个名字,其中之一函数的声明是这样的。 public fun <R, T> (suspend R.() -> T).createCoroutine( receiver: R, completion: ...

    这篇文章是在Kotlin协程的时候思考写下的。

    在Kotlin中,创建一个协程,需要调用createCoroutine函数,有两个函数叫这个名字,其中之一函数的声明是这样的。

    public fun <R, T> (suspend R.() -> T).createCoroutine(
        receiver: R,
        completion: Continuation<T>
    ): Continuation<Unit> = SafeContinuation(createCoroutineUnchecked(receiver, completion), COROUTINE_SUSPENDED)
    

    我们注意到 createCoroutine 是一个扩展函数,谁的扩展函数呢?suspend R.()->T 这个匿名函数的扩展函数。

    很神奇,为什么一个函数能有扩展函数呢?
    因为Kotlin中的匿名函数实际上也就是一个类,所以匿名函数当然可以有扩展函

    在这里插入图片描述

    所以这样写是完全没问题的,但是调用的位置就要注意了,必须是函数对象才能调用,下面的写法就无法调用到test1函数。

    在这里插入图片描述
    只能把函数转变为对象才可以调用
    在这里插入图片描述
    然后我们进入下一个问题,泛型的扩展函数的扩展函数是什么东西,我们把test1函数改一下,

    fun  <T> (T.() -> Unit).test1(): Unit {
    
    }
    

    这样,我们应该怎么调用这个函数呢,逆向思考,只有函数对象才能有扩展函数,那么T.()->Unit就应该是一个函数对象,而::doFunction就是一个对象啊,我们试一下。
    在这里插入图片描述

    果然没问题。但是泛型并没有发挥作用,因为doFunction函数是在调用的位置,才由函数转化为对象的,在doFuncion还是一个函数的时候,并不知道它会变成谁的匿名函数,所以完全跟泛型不搭边了,那这个位置加个泛型到底由什么用呢?往下分析。

    扩展函数有一个重要的属性,就是可以调用到其Reciver类中对外公开的属性和方法。给扩展函数加一个泛型,就是为了调用到泛型内部的公开属性和方法。
    我们换个写法,模仿一下KT的协程里面场景。

    先写个接口,模仿KT协程里面的 Coroutine类
    在这里插入图片描述
    再写个类,模拟协程调用的位置
    在这里插入图片描述
    我们发现,有泛型的方法,可以获取到一个this。 因为上一个Demo中doFunction不是一个匿名函数,且本来就是MainActivity类的成员,所以即使不把扩展函数成泛型写法,也可以获取到MainActivity的成员,所以看不出来差别。
    但是在下面这个Demo中,由于block函数成为了泛型T ,也就是TestInterface的扩展函数,所以可以调用到TestInterface的这个This,而没有泛型的方法则无法调用到。

    展开全文
  • Is it possible to access extension functions from Java code?I defined the extension function in a Kotlin file.package com.test.extensionsimport com.test.model.MyModel/****/public fun MyModel.bar(): In...
  • kotlin的扩展方法,其实是以java的静态方法形式存在的,也就是说如果要用java调用kotlin的扩展方法,和调用静态函数一样调用扩展属性也是相同的道理举个例子,我们在某个kotlin文件(文件名为Utils.kt)里为Throwable...
  • Kotlin 扩展函数的原理

    2021-04-05 16:04:44
    Kotlin有一个非常好的特性,就是扩展函数,非常好用如下 package com.plbear.leakcanary import android.app.Activity import android.util.Log fun logcat(msg: String?) { Log.e("yanlog", msg ?: "null") } ...
  • kotlin增加静态扩展函数

    千次阅读 2021-11-15 19:32:46
    比方说要为String增加一个cmpByLength方法,并且希望是静态的,可以创建一个StringEx.kt文件,里面这么写: fun String.Companion.cmpByLength(a: String,b: String): Boolean { return a.length>...
  • 1、扩展函数 首先看一下什么是扩展函数扩展函数表示即使在不修改某个类的源码的情况下,仍然可以打开这个类,向该类添加新的函数。 语法结构 fun ClassName.methodName(param1: Int, param2: Int): Int { return ...
  • Kotlin扩展函数

    2021-02-27 23:45:56
    Kotlin 扩展函数 1. 为什么需要扩展函数? 我们都知道 Koltin 这门语言与 Java 有非常好的互操作性,并且扩展函数这个新特性可以很平滑与现有Java 代码集成。甚至纯 Kotlin 的项目都可以基于 Java 库或者 Android ...
  • 一、何为扩展函数 就一句话 不改变原有类的情况下,扩展新的功能。 对于Java来说,扩展函数这一特性是没有的,但是Java中还是具体相同功能的特性,比如说继承,设计模式中的装饰模式。就功能来说,Kotlin中的扩展...
  • Kotlin扩展函数、扩展属性

    千次阅读 2021-12-03 15:50:45
    扩展函数 扩展属性 kotlin
  • 扩展函数和扩展属性扩展函数 扩展函数和扩展属性是Kotlin的新特性,对标Java的话,就是方法二次封装。 扩展函数
  • 八、kotlin扩展函数

    2021-10-13 21:11:37
    视频课 视频老师的博客 提供架构的易用性 减少代码量,让代码更加整洁、纯粹 提高编码的效率,生产力提高 1.扩展方法 扩展方法的原型 fun String.lastChar(): Char = this.get(this...//扩展函数的定义,就是在方法
  • 文章目录5.6 扩展函数和运算符重载5.6.1 大有用途的扩展函数5.6.2 有趣的运算符重载5.7 小结与点评 5.6 扩展函数和运算符重载 5.6.1 大有用途的扩展函数 扩展函数表示即使在不修改某个类的源码的情况下,仍然可以...
  • Kotlin之扩展函数

    2020-12-28 10:51:15
    Kotlin之扩展函数 ** Kotlin里面 函数是一种类型(函数类型) 也是一种对象(函数对象) 在函数名前加双冒号(::)即为此函数的函数对象 扩展函数对象的调用方法 fun String.a() { TODO() } fun test() { String::a....
  • kotlin 扩展函数作为闭包参数 fun LiveData.captureValues(block: LiveDataValueCapture.() -> Unit) { val capture = LiveDataValueCapture() capture .block() }
  • 注:编码工具为IntelliJ 目录 案例一: 案例二: 案例三: 案例一: ... // 看到lambda里面的花括号,想到类的成员函数时高阶函数,省略了this. textview { println("textview") } button { pri
  • 扩展函数和运算符重载 一、扩展函数 (一)什么是扩展函数扩展函数表示即使在不修改某个类的源码的情况下,仍然可以打开这个类,向该类添加新的函数。 (二)语法结构 定义扩展函数的语法结构: fun ClassName....
  • kotlin中的扩展函数,实际上是在自己的类中添加了一个static final方法,将需要扩展的类,在使用的时候作为第一个参数传入方法中,然后使用。比如: 在ExtensionTest.kt中的顶级函数 fun String.hello(str: ...
  • 在PHP中获取扩展名,可以用内置的PHP函数,不过或多或少都会有些问题,所以还是自己写一个,为了大家使用方便,加入注释,相信懂PHP的,都应该知道本函数是如何用的。PHP自定义获取上传文件扩展函数...
  • use是Kotlin的一个内置的扩展函数,它能保证Lambda表达式中的代码全部执行完之后自动将外层的流关闭,这样我们就不需要再写一个finally语句,手动关闭流了。使用方法如下: fun save(inputText: String) { try { ...
  • Java过渡Kotlin06:扩展

    2021-04-14 17:33:29
    1.是什么 Kotlin 可以对一个类的属性和方法进行扩展,且不需要继承或.../**扩展函数**/ fun User.Print(){ print("用户名 $name") } fun main(arg:Array<String>){ var user = User("Runoob") user.Print() }
  • 此示例使用继承来扩展原始对象.命名仅用于说明.class Test {baseMethod() {}}class TestWithClose ...更新您已在评论中提到可以按照自己的方式编写内置函数扩展方法,我可以看到您希望对自己的代码执行相同的操...
  • 点扩散函数(PSF)调制

    千次阅读 2021-04-24 14:15:33
    点扩散函数点扩展函数PSF(point spread function )描述了成像系统对点源或点对象的响应。PSF更一般的术语称为系统的脉冲响应(impulse response),PSF是聚焦光学系统的脉冲响应。从功能上讲,它是成像系统光学传递...
  • 第 33 卷第 4 期 红外与激光工程 2004 年 8 月 Vol. 33No. 4 Infrared and Laser Engineering... 2004 点扩散函数的一维数值计算及其 MATLAB实现3江月松1 , 邱志伟2 ,李 铮1 (1. 北京航空航天大学 电子信息工程学院 ...
  • 网上有一些关于获取文件扩展名的资料,粗略看了一下,有很多bug,自己写一个,望指导/*** 获取文件扩展名*author province* @param unknown_type $file_name* @return $ex_name*/function get_exname($file_name){if...
  • 增强功能函数,可以将功能代码聚合,组件层级变浅,代码量少. 1.1、简介 在React 的世界中,有容器组件和 UI 组件之分,在 React Hooks 出现之前,UI 组件我们可以使用函数,无状态组件来展示 UI,而对于容器组件,...
  • 我们在宝塔 Linux 面板中安装环境(如Nginx 或 Apache、PHP 等)一般都不需要对 PHP 进行设置,不过某些环境下 PHP 需要安装一些必要的扩展,也有可能需要禁用一些函数,那么在宝塔 Linux 面板中应该如何操作呢?...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 1,309,945
精华内容 523,978
关键字:

扩展函数