您的位置:

有关java存储(java 文件存储)

本文目录一览:

java变量存储问题

我对你看到的这个东西很不认同啊,Java里对int类型是传值i的,你定义了两个不同的int类型变量a和b那么它们就是毫无关系的,应该是不同的两个地址才对。

凭我对编译原理的理解,我觉得Java和C什么的一样,对局部变量是这样处理的:

程序在编译的时候就会给变量分配其在栈中的位置。举个例子:

int a = 3; int b = 3;

int c = a + 1;

假设编译时给a分配的地址是“栈底+8”,b的地址是“栈底+12”,c的地址是“栈底+16”,那么这一段代码编译后变成:

mov 8(%ebp), 3

mov 12(%ebp), 3

add 16(%ebp), 8(%ebp), 1

也就是说编译之后,程序里就没有a、b这些东西了,直接通过地址来进行运算。

如果我上面的理解没有问题,那么对你的问题的回答是:

1)不用找。

2)不会改变,这个地址在编译时就分配好了。

3)我认为函数传参的时候对基本类型还是传值的,即会把基本类型的参数的值复制一份放到被调用函数的栈中;对于类变量才是直接扔进去一个地址。不过我不是很确定。

后补充的那一问,没错我同意你的看法。

北大青鸟java培训:互联网环境下数据存储方法与渠道?

随着互联网的不断发展,用户在数据存储方面可以使用的渠道也在不断的增加,而将数据存储到云空间之中的话,大大提高了数据的可移动性。

今天,我们就一起来了解和学习一下关于数据存储方面的一些知识。

通常,在使用任何编程语言进行编程时,您需要使用各种变量来存储各种信息。

变量只是保留值的存储位置。

这意味着,当你创建一个变量,你必须在内存中保留一些空间来存储它们。

您可能想存储各种数据类型的信息,如字符,宽字符,整数,浮点,双浮点,布尔等。

基于变量的数据类型,操作系统分配内存并决定什么可以存储在保留内存中。

与其他编程语言(如C中的C和java)相反,变量不会声明为某种数据类型。

变量分配有R对象,R对象的数据类型变为变量的数据类型。

尽管有很多类型的R对象,但经常使用的是:向量矩阵数组因子数据帧列表(1)基本数据类型这些对象中简单的是向量对象,并且这些向量有六种数据类型,也称为六类向量。

其他R对象建立在原子向量之上。

数据类型例校验Logical(逻辑型)TRUE,FALSEv-TRUEprint(class(v))它产生以下结果-[1]"logical"Numeric(数字)12.3,5,999v-23.5print(class(v))它产生以下结果-[1]"numeric"Integer(整型)2L,34L,0Lv-2Lprint(class(v))它产生以下结果-[1]"integer"Complex(复合型)3+2iv-2+5iprint(class(v))它产生以下结果-[1]"complex"Character(字符)'a','"good","TRUE",'23.4'v-"TRUE"print(class(v))它产生以下结果-[1]"character"Raw(原型)"Hello"被存储为48656c6c6fv-charToRaw("Hello")print(class(v))它产生以下结果-[1]"raw"在R编程中,非常基本的数据类型是称为向量的R对象,其保存如上所示的不同类的元素。

请注意,在R中,类的数量不仅限于上述六种类型。

例如,我们可以使用许多原子向量并创建一个数组,其类将成为数组。

(2)Vectors向量当你想用多个元素创建向量时,你应该使用c()函数,这意味着将元素组合成一个向量。

#Createavector.apple-c('red','green',"yellow")print(apple)#Gettheclassofthevector.print(class(apple))当我们执行上面的代码,它产生以下结果[1]"red""green""yellow"[1]"character"(3)Lists列表列表是一个R对象,它可以在其中包含许多不同类型的元素,如向量,函数甚至其中的另一个列表。

#Createalist.list1-list(c(2,5,3),21.3,sin)#Printthelist.print(list1)当我们执行上面的代码,它产生以下结果[[1]][1]253[[2]][1]21.3[[3]]function(x).Primitive("sin")(4)Matrices矩阵矩阵是二维矩形数据集。

它可以使用矩阵函数的向量输入创建。

#Createamatrix.M=matrix(c('a','a','b','c','b','a'),nrow=2,ncol=3,byrow=TRUE)print(M)当我们执行上面的代码,它产生以下结果[,1][,2][,3][1,]"a""a""b"[2,]"c""b""a"(5)Arrays数组虽然矩阵被限制为二维,但阵列可以具有任何数量的维度。

数组函数使用一个dim属性创建所需的维数。

在下面的例子中,我们创建了一个包含两个元素的数组,每个元素为3x3个矩阵。

#Createanarray.a-array(c('green','yellow'),dim=c(3,3,2))print(a)当我们执行上面的代码,它产生以下结果,,1[,1][,2][,3][1,]"green""yellow""green"[2,]"yellow""green""yellow"[3,]"green""yellow""green",,2[,1][,2][,3][1,]"yellow""green""yellow"[2,]"green""yellow""green"[3,]"yellow""green""yellow"(6)Factors因子因子是使用向量创建的r对象。

北京北大青鸟认为它将向量与向量中元素的不同值一起存储为标签。

标签总是字符,不管它在输入向量中是数字还是字符或布尔等。

它们在统计建模中非常有用。

问个有关JAVA内存存储和关系比较的小问题。

这不关是不是变量的问题,

JDK5 之后 基础类型和基包装类型会运算的时候boxing 和 unboxig.

当 基本类型 int 和 对象类型的Integer 比较时Integer 会自动unboxing ,对于基本类型的数据当然是比较值,而不是地址了。

java 中的基本类型有 boolean ,byte,int double,float,long 这些你都可以试验证一下,结果都是一样的 .例如:

boolean b=false;

Boolean b2 = new Boolean(false);

Boolean b3 = new Boolean(false);

System.out.println(b==b2);

System.out.println(b3==b2);

执行存储过程有多少种方法java

Java执行存储过程的方法:

简单的老的JDBC通过CallableStatement类支持存储过程的调用。该类实际上是PreparedStatement的一个子类。假设有一个poets数据库。数据库中有一个设置诗人逝世年龄的存储过程。下面是对老酒鬼Dylan Thomas(old soak Dylan Thomas,不指定是否有关典故、文化,请批评指正。译注)进行调用的详细代码: 

try{

       int age = 39; 

      String poetName = "dylan thomas"; 

      CallableStatement proc = connection.prepareCall("{ call set_death_age(?, ?) }"); 

      proc.setString(1, poetName); 

      proc.setInt(2, age); 

      cs.execute();

}catch (SQLException e){ // ....}

传给prepareCall方法的字串是存储过程调用的书写规范。它指定了存储过程的名称,?代表了需要指定的参数。 

和JDBC集成是存储过程的一个很大的便利:为了从应用中调用存储过程,不需要存根(stub)类或者配置文件,除了你的DBMS的JDBC驱动程序外什么也不需要。 

当这段代码执行时,数据库的存储过程就被调用。我们没有去获取结果,因为该存储过程并不返回结果。执行成功或失败将通过例外得知。失败可能意味着调用存储过程时的失败(比如提供的一个参数的类型不正确),或者一个应用程序的失败(比如抛出一个例外指示在poets数据库中并不存在“Dylan Thomas”) 

结合SQL操作与存储过程 

映射Java对象到SQL表中的行相当简单,但是通常需要执行几个SQL语句;可能是一个SELECT查找ID,然后一个INSERT插入指定ID的数据。在高度规格化(符合更高的范式,译注)的数据库模式中,可能需要多个表的更新,因此需要更多的语句。Java代码会很快地膨胀,每一个语句的网络开销也迅速增加。 

将这些SQL语句转移到一个存储过程中将大大简化代码,仅涉及一次网络调用。所有关联的SQL操作都可以在数据库内部发生。并且,存储过程语言,例如PL/SQL,允许使用SQL语法,这比Java代码更加自然。早期的存储过程,使用Oracle的PL/SQL语言编写: 

create procedure set_death_age(poet VARCHAR2, poet_age NUMBER) 

      poet_id NUMBER;

      begin SELECT id INTO poet_id FROM poets WHERE name = poet; 

      INSERT INTO deaths (mort_id, age) VALUES (poet_id, poet_age);

end set_death_age;

set_death_age几乎可以肯定是一个很烂的实现。应该在poets表中添加一列来存储逝世年龄。Java代码中并不关心数据库模式是怎么实现的,因为它仅调用存储过程。以后可以改变数据库模式以提高性能,但是不必修改代码。 

下面是调用上面存储过程的Java代码: 

public static void setDeathAge(Poet dyingBard, int age) throws SQLException{ 

      Connection con = null; 

      CallableStatement proc = null; 

      try {

           con = connectionPool.getConnection(); 

           proc = con.prepareCall("{ call set_death_age(?, ?) }");

           proc.setString(1, dyingBard.getName()); 

            proc.setInt(2, age); 

            proc.execute(); 

     finally {  

           try { proc.close(); } 

           catch (SQLException e) {}  

            con.close(); 

     }

}

为了确保可维护性,建议使用像这儿这样的static方法。这也使得调用存储过程的代码集中在一个简单的模版代码中。如果用到许多存储过程,就会发现仅需要拷贝、粘贴就可以创建新的方法。因为代码的模版化,甚至也可以通过脚本自动生产调用存储过程的代码。 

Functions 

存储过程可以有返回值,所以CallableStatement类有类似getResultSet这样的方法来获取返回值。当存储过程返回一个值时,必须使用registerOutParameter方法告诉JDBC驱动器该值的SQL类型是什么。也必须调整存储过程调用来指示该过程返回一个值。 

下面接着上面的例子。这次查询Dylan Thomas逝世时的年龄。这次的存储过程使用PostgreSQL的pl/pgsql: 

create function snuffed_it_when (VARCHAR) returns integer 'declare 

                 poet_id NUMBER; 

                 poet_age NUMBER;

begin 

--first get the id associated with the poet. 

               SELECT id INTO poet_id FROM poets WHERE name = $1;

--get and return the age. 

                 SELECT age INTO poet_age FROM deaths WHERE mort_id = poet_id; 

return age;

end;' language 'pl/pgsql';

另外,注意pl/pgsql参数名通过Unix和DOS脚本的$n语法引用。同时,也注意嵌入的注释,这是和Java代码相比的另一个优越性。在Java中写这样的注释当然是可以的,但是看起来很凌乱,并且和SQL语句脱节,必须嵌入到Java String中。 

下面是调用这个存储过程的Java代码: 

connection.setAutoCommit(false);

CallableStatement proc = connection.prepareCall("{ ? = call snuffed_it_when(?) }");

proc.registerOutParameter(1, Types.INTEGER);

proc.setString(2, poetName);

cs.execute();

int age = proc.getInt(2);

如果指定了错误的返回值类型会怎样?那么,当调用存储过程时将抛出一个RuntimeException,正如你在ResultSet操作中使用了一个错误的类型所碰到的一样。 

复杂的返回值 

如果这是存储过程的全部功能,那么存储过程就不是其它远程执行机制的替换方案了。存储过程的功能比这强大得多。 

当执行一个SQL查询时,DBMS创建一个叫做cursor(游标)的数据库对象,用于在返回结果中迭代每一行。ResultSet是当前时间点的游标的一个表示。这就是为什么没有缓存或者特定数据库的支持,只能在ResultSet中向前移动。 

某些DBMS允许从存储过程中返回游标的一个引用。JDBC并不支持这个功能,但是Oracle、PostgreSQL和DB2的JDBC驱动器都支持在ResultSet上打开到游标的指针(pointer)。 

设想列出所有没有活到退休年龄的诗人,下面是完成这个功能的存储过程,返回一个打开的游标,同样也使用PostgreSQL的pl/pgsql语言: 

create procedure list_early_deaths () return refcursor as 'declare 

      toesup refcursor;

begin 

      open toesup for SELECT poets.name, deaths.age FROM poets, deaths -- all entries in deaths are for poets. -- but the table might become generic. 

      WHERE poets.id = deaths.mort_id AND deaths.age  60; 

      return toesup;

end;' language 'plpgsql';

下面是调用该存储过程的Java方法,将结果输出到PrintWriter: 

PrintWriter: 

static void sendEarlyDeaths(PrintWriter out){ 

      Connection con = null;

      CallableStatement toesUp = null;

      try {

          con = ConnectionPool.getConnection(); 

           // PostgreSQL needs a transaction to do this... con.

          setAutoCommit(false); // Setup the call. 

          CallableStatement toesUp = connection.prepareCall("{ ? = call list_early_deaths () }"); 

           toesUp.registerOutParameter(1, Types.OTHER); 

           toesUp.execute(); 

           ResultSet rs = (ResultSet) toesUp.getObject(1); 

           while (rs.next()) {

                  String name = rs.getString(1);

                  int age = rs.getInt(2); 

                  out.println(name + " was " + age + " years old."); 

            } 

            rs.close(); 

         }  

       catch (SQLException e) { // We should protect these calls. toesUp.close(); con.close();

      }

}

因为JDBC并不直接支持从存储过程中返回游标,使用Types.OTHER来指示存储过程的返回类型,然后调用getObject()方法并对返回值进行强制类型转换。 

这个调用存储过程的Java方法是mapping的一个好例子。Mapping是对一个集上的操作进行抽象的方法。不是在这个过程上返回一个集,可以把操作传送进去执行。本例中,操作就是把ResultSet打印到一个输出流。这是一个值得举例的很常用的例子,下面是调用同一个存储过程的另外一个方法实现: 

public class ProcessPoetDeaths{ 

      public abstract void sendDeath(String name, int age);

}

      static void mapEarlyDeaths(ProcessPoetDeaths mapper){ 

      Connection con = null; 

      CallableStatement toesUp = null; 

      try {

           con = ConnectionPool.getConnection(); 

           con.setAutoCommit(false); 

           CallableStatement toesUp = connection.prepareCall("{ ? = call list_early_deaths () }");

            toesUp.registerOutParameter(1, Types.OTHER); 

            toesUp.execute(); 

            ResultSet rs = (ResultSet) toesUp.getObject(1); 

           while (rs.next()) { 

           String name = rs.getString(1); 

           int age = rs.getInt(2); 

          mapper.sendDeath(name, age); 

rs.close(); 

} catch (SQLException e) { // We should protect these calls. toesUp.close(); 

con.close(); 

}

}

这允许在ResultSet数据上执行任意的处理,而不需要改变或者复制获取ResultSet的方法: 

static void sendEarlyDeaths(final PrintWriter out){ 

            ProcessPoetDeaths myMapper = new ProcessPoetDeaths() { 

                                public void sendDeath(String name, int age) { 

                                                    out.println(name + " was " + age + " years old."); 

                               } 

           }; 

mapEarlyDeaths(myMapper);

}

这个方法使用ProcessPoetDeaths的一个匿名实例调用mapEarlyDeaths。该实例拥有sendDeath方法的一个实现,和我们上面的例子一样的方式把结果写入到输出流。当然,这个技巧并不是存储过程特有的,但是和存储过程中返回的ResultSet结合使用,是一个非常强大的工具。