当前位置: 首页 > 知识库问答 >
问题:

方法重载和原始类型如何工作?

唐康安
2023-03-14

我正在做Java类练习。我有一段代码,其中包含一个重载方法:

class A {

    // Overloaded method
    public void f(int n, float x) {
        System.out.println("f(int n, float x) n = " + n + " x = " + x);
    }

    private void f(long q, double y) {
        System.out.println("f(long q, double y) q = " + q + " y = " + y);
    }

    public void f(double y1, double y2) {
        System.out.println("f(double y1, double y2) y1 = " + y1 + " y2 = " + y2);
    }

    public void g() {
        int n = 1;
        long q = 12;
        float x = 1.5f;
        double y = 2.5;
        System.out.println("--- dans g ");
        f(n, q);
        f(q, n);
        f(n, x);
        f(n, y);
    }
}

主要:

public static void main(String[] args){ 
    A a = new A() ;
    a.g() ;
    System.out.println ("--- dans main") ;
    int n=1 ; 
    long q=12 ; 
    float x=1.5f ; 
    double y = 2.5 ;

    a.f(n, q) ; // my problem is here
    a.f(q, n) ; 
    a.f(n, x) ; 
    a.f(n, y) ;  
}

当我在main中调用方法a. f(n, q)时,我预计会出现错误,但它调用方法f(int n, flow x)而我的q是一个long数字,它的大小大于浮动的大小(8字节/4字节)所以我想知道这些原始类型是如何工作的?

共有3个答案

宣熙云
2023-03-14

以下19种基元类型的特定转换称为加宽基元转换:

字节到短、int、long、浮动或双精度

短到int、长、浮动或双精度

字符到int、long、float或double

int到long、float或double

长到浮动或加倍

浮动到双倍

扩展原始转换不会丢失有关数值整体大小的信息。

...

将int或long值转换为浮点,或将long值转换为double,可能会导致精度损失,也就是说,结果可能会丢失值的一些最低有效位。在这种情况下,生成的浮点值将是长值的正确四舍五入版本。

扶隐水
2023-03-14

long可以转换为浮动而不会引发错误。但您可能会失去精度。

有关详细信息,请参阅规格。

魏朗
2023-03-14

方法调用占据了规范中相当长的一部分。总而言之,编译器进行如下操作:

  1. 标识可能调用该方法的类。
  2. 识别那些可能被调用的类的方法。
  3. 如果确定了多个方法,请选择最具体的方法。

第2步是这里最有趣的一步:这分为许多步骤。总结一下:

  1. 如果类上有一个非varargs方法具有完全相同的参数类型(严格调用),请选择该方法
  2. 如果类上有一个非varargs方法,该方法的参数类型可以从实际参数中自动转换(松散调用),请选择该方法
  3. 如果类上有一个varargs方法,其参数类型与自动转换匹配,请选择该方法

您提供的参数和重载的任何参数类型都不完全匹配,所以您需要检查是否可以将这些参数转换为允许严格调用。严格调用中的转换为:

  • 身份转换(§5.1.1)

int可以通过标识转换为int来转换。long可以通过将原始转换扩展为浮动来转换。

因此f(int, flow)是适用的。

f(long,double)f(double,double)也适用,因为int可以扩展到long和double;并且可以将长扩展到双

但是,这些方法不如f(int,浮动)具体,因为int可以扩展为longDouble,而浮动可以扩展为Double。因此,根据JLS Sec15.12.2.5中列出的非正式直觉,这些方法不如f(int,浮动)具体。因此,f(int,浮动)是被调用的方法。

 类似资料:
  • JavaScript 允许我们像使用对象一样使用原始类型(字符串,数字等)。JavaScript 还提供了这样的调用方法。我们很快就会学习它们,但是首先我们将了解它的工作原理,毕竟原始类型不是对象(在这里我们会分析地更加清楚)。 我们来看看原始类型和对象之间的关键区别。 一个原始值: 是原始类型中的一种值。 在 JavaScript 中有 7 种原始类型:string,number,bigint,

  • 问题内容: 我正在尝试这样做,但是不起作用: 我应该如何正确地做到这一点? 问题答案: 您不能,因为基元不是对象。 您目前正在尝试的还没有实例化- 它正在加载一个类。但是您不能对原始对象执行此操作。确实是用于类型的名称,无论何时获取其对象(例如,通过反射),但您都无法使用加载它。 参考:反射教程: 如果一个类的全限定名称可用,则可以使用静态方法Class.forName()获得相应的Class。

  • 当由于类型提升而存在多个可接受的方法时,决定将执行哪种方法的因素是什么? 这是示例代码 输出是:如所写,但如果我注释掉 为什么?它是否尝试做最少的类型推广?它是否试图提升论点1,然后提升论点2?它是基于某种类型的优先级吗? 我见过这个问题:方法重载和基元类型是如何工作的?,其中包括以下声明: 我要求在所有可能的方法中如何选择要执行的最终方法背后的更多细节。我知道会发生类型提升,但如果类型提升后有多

  • 问题内容: 我想对原始类型和引用类型之间的Java中的isAssignableFrom行为有一个更好的了解。 例如: 我知道在分配基元<->引用时会根据需要进行装箱/拆箱,但是我想过,因此isAssignableFrom在上面的前两个示例中将返回true。 有人可以解释为什么它返回false,这里合适的测试是什么? 问题答案: 您 实际上 不能为变量分配值-但可以使用自动装箱从 转换为。 该Jav

  • 如果类型参数在创建期间传递了npt,则原始类型是泛型类或接口的对象。 以下示例将展示上述概念。 例子 (Example) 使用您选择的任何编辑器创建以下Java程序。 GenericsTester.java package com.wenjiangs; public class GenericsTester { public static void main(String[] args) {

  • 问题内容: 如果有两个方法,则它们具有不同的参数,并且它们的返回类型也 不同 。像这样: 如果返回类型相同,则当然是 重载 。但是由于返回类型 不同 ,我们还可以将其视为 过载 吗? 问题答案: 考虑过载的以下几点: 在Java中重载方法的首要原则是更改方法签名。方法签名由参数数量,参数类型和参数顺序(如果它们是不同类型)组成。 } 方法的返回类型从不属于方法签名的一部分,因此仅更改方法的返回类型