我似乎无法解决我的.pm文件和脚本的问题。我对Perl相当陌生。
我有一个名为"project“的数据库,还有一个名为”name“的表。邮件表有7个条目,我想使用模块来显示。
因此,我有这个自定义模块来登录到数据库并执行查询。这个模块名为DB.pm
DB.pm存储在我的FEDORA 20上/root/mysql/GUI/DB.pm.
DB.pm的定义如下:
package GUI::DB;
use strict;
use DBI;
use vars qw(@ISA @EXPORT);
use Exporter;
@ISA = qw(Exporter);
@EXPORT = qw(dbConnect query);
#
# dbConnect - connect to the database, get the database handle
#
sub dbConnect {
# Read database settings from config file:
print "Works";
my $dsn = "DBI:mysql:project";
my $dbh = DBI->connect( $dsn,
'root',
'mydatabasepassword',
{ RaiseError => 1 }
);
return $dbh;
}
#
# query - execute a query with parameters
# query($dbh, $sql, @bindValues)
#
sub query {
my $dbh = shift;
my $sql ="SELECT * FROM mailing";
my @bindValues = @_; # 0 or serveral parameters
my @returnData = ();
# issue query
my $sth = $dbh->prepare($sql); //**line number 39 that is giving** error
if ( @bindValues ) {
$sth->execute(@bindValues);
} else {
$sth->execute();
}
if ( $sql =~ m/^select/i ) {
while ( my $row = $sth->fetchrow_hashref ) {
push @returnData, $row;
}
}
# finish the sql statement
$sth->finish();
return @returnData;
}
1;现在,我想在我的每个脚本中使用这个模块。这就是我试过的:
#!/usr/bin/perl
use warnings;
use strict;
use lib '/root/mysql/';
use GUI::DB qw(dbConnect query);
dbConnect();
query();这就是我要犯的错误-->
不能在/root/mysql/GUI/DB.pm第39行的未定义值上调用方法“准备”
请帮我处理这个。我不知道该如何进行。我猜这与争论的通过有关。数据库没有什么问题。它从CLI可以很好的工作。
谢谢:)
_x_X_X_X_X_X_X_X_X_X_X_X_X_X_X_X__X_X_X_X_X__X
直到这一切都解决了
_X_X_X_X_X_X_X_X_X_X_X_X_X_X_X_X_X__X_X_X
进一步的问题是SQL命令无法工作。在我的数据库邮件表中,我有具有不同域的电子邮件id。例如,一些id是xyz@gmail.com、12343@gmail.com、bae@yahoo.com等,我假设每天都会向具有不同域的邮件表添加新的电子邮件id。
我正在尝试编写一个脚本来更新另一个表,该表保存了他们的域名的电子邮件地址的每日计数。这就是我尝试过的:
#!/usr/bin/perl
use warnings;
use strict;
use lib '/root/mysql/';
use 5.016;
use Data::Dumper;
use GUI::DB qw(dbConnect query);
my $data = dbConnect();
my @domain = query($data, "SELECT substr(addr,locate('\@',addr)+1) as maildomain, count (*) as mailcount FROM mailing GROUP BY maildomain ORDER BY mailcount DESC");
for my $key (@domain){
say Dumper ($key);
}但我搞错了,
您的SQL语法有错误;请检查与MariaDB服务器版本相对应的手册,以获得正确的语法,以便在/root/mysql/GUI/DB.pm第44行按邮件组按邮件域顺序从邮件组中使用邮件计数DESC。
相同的SQL语句在CLI中工作,没有任何问题。任何帮助都将不胜感激。:)
发布于 2015-01-17 22:07:14
1)您的错误是在这里没有定义$dbh:
sub query {
my $dbh = shift;
...
# issue query
my $sth = $dbh->prepare($sql); #<***LOOK HERE***...which意味着$dbh在这里必须是未定义的:
sub query {
my $dbh = shift; #<***LOOK HERE***
...
# issue query
my $sth = $dbh->prepare($sql); 2)让我们看看为什么。dbConnect()方法返回$dbh:
sub dbConnect {
# Read database settings from config file:
print "Works";
my $dsn = "DBI:mysql:project";
my $dbh = DBI->connect(
$dsn,
'root',
'mydatabasepassword',
{ RaiseError => 1 }
);
return $dbh; #<***LOOK HERE*****
}但是,您可以这样调用dbConnect():
dbConnect();因为您从未将返回值保存在任何地方,所以$dbh将被丢弃。
4)此外,您还像这样调用query():
query();然而,您像这样定义了query():
sub query {
my $dbh = shift;query() sub相信第一个参数将是数据库句柄--但是您没有使用任何参数调用query()。
你需要这样做:
my $data_base_handle = dbConnect();
my @results = query($data_base_handle);
#do something with @results对评论的回应
我打印了@results,这就是我看到的散列(0x1d05be8)散列(0x1d05ba0)散列(0x1d05b58)散列(0x1d05b10)散列(0x1d05ac8)散列(0x1d05a80)散列(0x1d05a38)
你写道:
my $row = $sth->fetchrow_hashref;...which要求DBI返回每一行作为对散列的引用。然后你写道:
push @returnData, $row;...which将每个散列引用推入一个数组中。所以query()返回一个哈希引用数组。当您打印哈希引用时,HASH(0x1d05be8)符号就是perl输出的内容。
如果您想要查看这些散列中的内容,请执行以下操作:
use 5.016; #enable say()
use Data::Dumper;
...
...
for my $href (@results) {
say Dumper($href);
}要访问散列引用中的数据,可以这样做:
use strict;
use warnings;
use 5.016;
use Data::Dumper;
my $href = {
c => 3,
a => 1,
b => 2,
};
my %hash = %{$href}; #dereference, {}, the reference into a hash, %
for my $key ( keys %hash ) {
say "$key $hash{$key}";
}
--output:--
c 3
a 1
b 2对下一条评论的回应:(在op下的评论中发布了答案)
顺便说一下,perl非常擅长文本处理,所以如果您无法解决查询中的问题,可以使用perl处理电子邮件地址:
use strict;
use warnings;
use 5.012;
use Data::Dumper;
use DBI;
use DBD::mysql;
# CONFIG VARIABLES
my $db_type = "mysql";
my $database = "my_db";
my $host = "localhost";
my $port = "3306";
my $user = "root";
my $pword = "";
# DATA SOURCE NAME
my $dsn = "dbi:$db_type:$database:$host:$port";
# PERL DBI CONNECT
my $dbh = DBI->connect($dsn, $user, $pword);
# PREPARE THE QUERY
my $tablename = "mailing";
my $select =<<"END_OF_SELECT";
select addr from $tablename
END_OF_SELECT
my $addr_aref = $dbh->selectcol_arrayref($select); #Returns a reference to a flat array containing all the email addresses
$dbh->disconnect;
my %count_for;
for my $addr (@{$addr_aref}) {
$addr =~ s/.*@//;
$count_for{$addr}++;
}
say Dumper(\%count_for);
--output:--
$VAR1 = {
'google.com' => 2,
'gorilla.com' => 1,
'yahoo.com' => 3
};https://stackoverflow.com/questions/28004708
复制相似问题